- 移除Emit模块下无用的Random Node Creator
- 修复RandomWithKey的byte[]为key的问题 - 重构MetadataModuleImpoterbackup
parent
856e924ed8
commit
d14d0f913c
|
@ -12,7 +12,7 @@ using UnityEngine.Assertions;
|
|||
|
||||
namespace Obfuz.Data
|
||||
{
|
||||
public class ModuleConstFieldAllocator : IModuleEmitManager
|
||||
public class ModuleConstFieldAllocator : IGroupByModuleEntity
|
||||
{
|
||||
private ModuleDef _module;
|
||||
private readonly IRandom _random;
|
||||
|
@ -138,7 +138,7 @@ namespace Obfuz.Data
|
|||
|
||||
private DefaultModuleMetadataImporter GetModuleMetadataImporter()
|
||||
{
|
||||
return MetadataImporter.Instance.GetDefaultModuleMetadataImporter(_module);
|
||||
return GroupByModuleManager.Ins.GetDefaultModuleMetadataImporter(_module);
|
||||
}
|
||||
|
||||
private void CreateCCtorOfRvaTypeDef(TypeDef type)
|
||||
|
@ -268,7 +268,7 @@ namespace Obfuz.Data
|
|||
|
||||
private ModuleConstFieldAllocator GetModuleAllocator(ModuleDef mod)
|
||||
{
|
||||
return EmitManager.Ins.GetEmitManager<ModuleConstFieldAllocator>(mod, () => new ModuleConstFieldAllocator(_encryptor, _random, _rvaDataAllocator));
|
||||
return GroupByModuleManager.Ins.GetEntity<ModuleConstFieldAllocator>(mod, () => new ModuleConstFieldAllocator(_encryptor, _random, _rvaDataAllocator));
|
||||
}
|
||||
|
||||
public FieldDef Allocate(ModuleDef mod, int value)
|
||||
|
@ -303,7 +303,7 @@ namespace Obfuz.Data
|
|||
|
||||
public void Done()
|
||||
{
|
||||
foreach (var moduleAllocator in EmitManager.Ins.GetEmitManagers<ModuleConstFieldAllocator>())
|
||||
foreach (var moduleAllocator in GroupByModuleManager.Ins.GetEntities<ModuleConstFieldAllocator>())
|
||||
{
|
||||
moduleAllocator.Done();
|
||||
}
|
||||
|
|
|
@ -25,7 +25,7 @@ namespace Obfuz.Data
|
|||
}
|
||||
}
|
||||
|
||||
public class ModuleRvaDataAllocator : ModuleEmitManagerBase
|
||||
public class ModuleRvaDataAllocator : GroupByModuleEntityBase
|
||||
{
|
||||
// randomized
|
||||
const int maxRvaDataSize = 0x1000;
|
||||
|
@ -234,7 +234,7 @@ namespace Obfuz.Data
|
|||
cctorMethod.Body = body;
|
||||
var ins = body.Instructions;
|
||||
|
||||
DefaultModuleMetadataImporter importer = MetadataImporter.Instance.GetDefaultModuleMetadataImporter(mod);
|
||||
DefaultModuleMetadataImporter importer = GroupByModuleManager.Ins.GetDefaultModuleMetadataImporter(mod);
|
||||
foreach (var field in _rvaFields)
|
||||
{
|
||||
// ldc
|
||||
|
@ -296,7 +296,7 @@ namespace Obfuz.Data
|
|||
|
||||
private ModuleRvaDataAllocator GetModuleRvaDataAllocator(ModuleDef mod)
|
||||
{
|
||||
return EmitManager.Ins.GetEmitManager<ModuleRvaDataAllocator>(mod, () => new ModuleRvaDataAllocator(_random, _encryptor));
|
||||
return GroupByModuleManager.Ins.GetEntity<ModuleRvaDataAllocator>(mod, () => new ModuleRvaDataAllocator(_random, _encryptor));
|
||||
}
|
||||
|
||||
public RvaData Allocate(ModuleDef mod, int value)
|
||||
|
@ -331,7 +331,7 @@ namespace Obfuz.Data
|
|||
|
||||
public void Done()
|
||||
{
|
||||
foreach (var allocator in EmitManager.Ins.GetEmitManagers<ModuleRvaDataAllocator>())
|
||||
foreach (var allocator in GroupByModuleManager.Ins.GetEntities<ModuleRvaDataAllocator>())
|
||||
{
|
||||
allocator.Done();
|
||||
}
|
||||
|
|
|
@ -1,17 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
using dnlib.DotNet.Emit;
|
||||
using NUnit.Framework;
|
||||
using Obfuz.Emit;
|
||||
using Obfuz.Data;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class CompileContext
|
||||
{
|
||||
public MethodDef method;
|
||||
public List<Instruction> output;
|
||||
public RvaDataAllocator rvaDataAllocator;
|
||||
public ConstFieldAllocator constFieldAllocator;
|
||||
}
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
using System;
|
||||
using UnityEngine.Assertions;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public struct ConstValue
|
||||
{
|
||||
public readonly DataNodeType type;
|
||||
public readonly object value;
|
||||
|
||||
public ConstValue(DataNodeType type, object value)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32: Assert.IsTrue(value is int); break;
|
||||
case DataNodeType.Int64: Assert.IsTrue(value is long); break;
|
||||
case DataNodeType.Float32: Assert.IsTrue(value is float); break;
|
||||
case DataNodeType.Float64: Assert.IsTrue(value is double); break;
|
||||
case DataNodeType.String: Assert.IsTrue(value is string); break;
|
||||
case DataNodeType.Bytes: Assert.IsTrue(value is byte[]); break;
|
||||
default: throw new NotSupportedException($"Unsupported type {type} for ConstValue");
|
||||
}
|
||||
this.type = type;
|
||||
this.value = value;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,12 +0,0 @@
|
|||
using Obfuz.Emit;
|
||||
using Obfuz.Utils;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public struct CreateExpressionOptions
|
||||
{
|
||||
public IRandom random;
|
||||
public IDataNodeCreator expressionCreator;
|
||||
public int depth;
|
||||
}
|
||||
}
|
|
@ -1,7 +0,0 @@
|
|||
namespace Obfuz.Emit
|
||||
{
|
||||
public abstract class DataNodeCreatorBase : IDataNodeCreator
|
||||
{
|
||||
public abstract IDataNode CreateRandom(DataNodeType type, object value, CreateExpressionOptions options);
|
||||
}
|
||||
}
|
|
@ -1,14 +0,0 @@
|
|||
namespace Obfuz.Emit
|
||||
{
|
||||
public enum DataNodeType
|
||||
{
|
||||
//Byte,
|
||||
Int32,
|
||||
Int64,
|
||||
Float32,
|
||||
Float64,
|
||||
String,
|
||||
Bytes,
|
||||
//Null,
|
||||
}
|
||||
}
|
|
@ -1,20 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
[NodeOutput(DataNodeType.Bytes)]
|
||||
public class BytesFromEncryptedBytesNode : DataNodeAny
|
||||
{
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
// only support Int32, int64, bytes.
|
||||
// string can only create from StringFromBytesNode
|
||||
// x = memcpy array.GetRange(index, length);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,78 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
using dnlib.DotNet.Emit;
|
||||
using Obfuz.Emit;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using static UnityEngine.Networking.UnityWebRequest;
|
||||
using UnityEngine.UIElements;
|
||||
using Obfuz.Data;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
[NodeOutput(DataNodeType.Int32)]
|
||||
[NodeOutput(DataNodeType.Int64)]
|
||||
[NodeOutput(DataNodeType.Float32)]
|
||||
[NodeOutput(DataNodeType.Float64)]
|
||||
[NodeOutput(DataNodeType.Bytes)]
|
||||
[NodeOutput(DataNodeType.String)]
|
||||
public class BytesInitializeFromFieldRvaDataNode : DataNodeAny
|
||||
{
|
||||
|
||||
private RvaData AllocateRvaData(CompileContext ctx)
|
||||
{
|
||||
ModuleDef mod = ctx.method.Module;
|
||||
RvaDataAllocator allocator = ctx.rvaDataAllocator;
|
||||
switch (Type)
|
||||
{
|
||||
//case DataNodeType.Int32: return allocator.Allocate(mod, IntValue);
|
||||
//case DataNodeType.Int64: return allocator.Allocate(mod, LongValue);
|
||||
//case DataNodeType.Float32: return allocator.Allocate(mod, FloatValue);
|
||||
//case DataNodeType.Float64: return allocator.Allocate(mod, DoubleValue);
|
||||
case DataNodeType.Bytes: return allocator.Allocate(mod, BytesValue);
|
||||
//case DataNodeType.String: return allocator.Allocate(mod, StringValue);
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {Type}.");
|
||||
}
|
||||
}
|
||||
|
||||
private static IMethod s_convertBytes;
|
||||
|
||||
private void InitImportMetadatas(ModuleDef mod)
|
||||
{
|
||||
if (s_convertBytes != null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
s_convertBytes = mod.Import(typeof(ConstUtility).GetMethod("InitializeArray", new[] { typeof(Array), typeof(byte[]), typeof(int), typeof(int) }));
|
||||
}
|
||||
|
||||
IMethod GetConvertMethod(ModuleDef mod)
|
||||
{
|
||||
InitImportMetadatas(mod);
|
||||
return s_convertBytes;
|
||||
}
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
// only support Int32, int64, bytes.
|
||||
// string can only create from StringFromBytesNode
|
||||
// x = memcpy array.GetRange(index, length);
|
||||
var output = ctx.output;
|
||||
RvaData rvaData = AllocateRvaData(ctx);
|
||||
ModuleDef mod = ctx.method.Module;
|
||||
IMethod convertMethod = GetConvertMethod(mod);
|
||||
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Ldsfld, rvaData.field));
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.offset));
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.size));
|
||||
//output.Add(Instruction.Create(OpCodes.Newarr, mod.CorLibTypes.Byte.ToTypeDefOrRef()));
|
||||
//output.Add(Instruction.Create(OpCodes.Ldc_I4, 0));
|
||||
//output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.size));
|
||||
output.Add(Instruction.Create(OpCodes.Call, convertMethod));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
[NodeOutput(DataNodeType.Int32)]
|
||||
[NodeOutput(DataNodeType.Int64)]
|
||||
public class ConstDataNode : DataNodeAny
|
||||
{
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
|
||||
// only Int32 - Null,
|
||||
// to avoid GC,
|
||||
// the leaf node that can create string or bytes is ConstFieldDataNode.
|
||||
// float and double can only come from RawCastAs int32 and int64.
|
||||
// so we only need to deal int32 and int64
|
||||
switch (Type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
// create ldloc.i4
|
||||
ctx.output.Add(Instruction.CreateLdcI4(IntValue));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
// create ldloc.i8
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Ldc_I8, LongValue));
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
throw new NotImplementedException($"Type:{Type} not implemented");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
using System.Collections.Generic;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
[NodeOutput(DataNodeType.Int32)]
|
||||
[NodeOutput(DataNodeType.Int64)]
|
||||
[NodeOutput(DataNodeType.Bytes)]
|
||||
public class ConstExpression : DataNodeAny
|
||||
{
|
||||
public IFunction function;
|
||||
public readonly List<IDataNode> inputs;
|
||||
public readonly ConstValue result;
|
||||
|
||||
public ConstExpression(IFunction function, List<IDataNode> inputs, ConstValue result)
|
||||
{
|
||||
this.function = function;
|
||||
this.inputs = inputs;
|
||||
Type = result.type;
|
||||
this.result = result;
|
||||
}
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
function.Compile(ctx, inputs, result);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,60 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using System.Runtime.CompilerServices;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class ConstFieldDataNode : DataNodeAny
|
||||
{
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
ModuleDef mod = ctx.method.Module;
|
||||
var output = ctx.output;
|
||||
FieldDef field;
|
||||
switch (Type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
field = ctx.constFieldAllocator.Allocate(mod, IntValue);
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
field = ctx.constFieldAllocator.Allocate(mod, LongValue);
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Float32:
|
||||
{
|
||||
field = ctx.constFieldAllocator.Allocate(mod, FloatValue);
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Float64:
|
||||
{
|
||||
field = ctx.constFieldAllocator.Allocate(mod, DoubleValue);
|
||||
break;
|
||||
}
|
||||
case DataNodeType.String:
|
||||
{
|
||||
field = ctx.constFieldAllocator.Allocate(mod, StringValue);
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Bytes:
|
||||
{
|
||||
// ldsfld
|
||||
// ldtoken
|
||||
// RuntimeHelpers.InitializeArray(array, fieldHandle);
|
||||
//break;
|
||||
throw new NotSupportedException("Bytes not supported");
|
||||
}
|
||||
default:
|
||||
{
|
||||
throw new NotImplementedException($"Type:{Type} not implemented");
|
||||
}
|
||||
}
|
||||
output.Add(Instruction.Create(OpCodes.Ldsfld, field));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,19 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class ConstFromBytesNode : DataNodeAny
|
||||
{
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
// only support Int32, int64, bytes.
|
||||
// string can only create from StringFromBytesNode
|
||||
// x = memcpy array.GetRange(index, length);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,117 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
using dnlib.DotNet.Emit;
|
||||
using Obfuz.Emit;
|
||||
using System;
|
||||
using Obfuz.Data;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
[NodeOutput(DataNodeType.Int32)]
|
||||
[NodeOutput(DataNodeType.Int64)]
|
||||
[NodeOutput(DataNodeType.Float32)]
|
||||
[NodeOutput(DataNodeType.Float64)]
|
||||
[NodeOutput(DataNodeType.Bytes)]
|
||||
[NodeOutput(DataNodeType.String)]
|
||||
public class ConstFromFieldRvaDataNode : DataNodeAny
|
||||
{
|
||||
|
||||
private RvaData AllocateRvaData(CompileContext ctx)
|
||||
{
|
||||
ModuleDef mod = ctx.method.Module;
|
||||
RvaDataAllocator allocator = ctx.rvaDataAllocator;
|
||||
switch (Type)
|
||||
{
|
||||
case DataNodeType.Int32: return allocator.Allocate(mod, IntValue);
|
||||
case DataNodeType.Int64: return allocator.Allocate(mod, LongValue);
|
||||
case DataNodeType.Float32: return allocator.Allocate(mod, FloatValue);
|
||||
case DataNodeType.Float64: return allocator.Allocate(mod, DoubleValue);
|
||||
case DataNodeType.Bytes: return allocator.Allocate(mod, BytesValue);
|
||||
case DataNodeType.String: return allocator.Allocate(mod, StringValue);
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {Type}.");
|
||||
}
|
||||
}
|
||||
|
||||
private static IMethod s_convertInt;
|
||||
private static IMethod s_convertLong;
|
||||
private static IMethod s_convertFloat;
|
||||
private static IMethod s_convertDouble;
|
||||
|
||||
private static IMethod s_convertString;
|
||||
//private static IField s_Encoding_Utf8;
|
||||
private static IMethod s_convertBytes;
|
||||
|
||||
private void InitImportMetadatas(ModuleDef mod)
|
||||
{
|
||||
if (s_convertInt != null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
s_convertInt = mod.Import(typeof(ConstUtility).GetMethod("GetInt", new[] { typeof(byte[]), typeof(int) }));
|
||||
s_convertLong = mod.Import(typeof(ConstUtility).GetMethod("GetLong", new[] { typeof(byte[]), typeof(int) }));
|
||||
s_convertFloat = mod.Import(typeof(ConstUtility).GetMethod("GetFloat", new[] { typeof(byte[]), typeof(int) }));
|
||||
s_convertDouble = mod.Import(typeof(ConstUtility).GetMethod("GetDouble", new[] { typeof(byte[]), typeof(int) }));
|
||||
s_convertString = mod.Import(typeof(ConstUtility).GetMethod("GetString", new[] { typeof(byte[]), typeof(int), typeof(int) }));
|
||||
//s_Encoding_Utf8 = mod.Import(typeof(Encoding).GetField("UTF8"));
|
||||
s_convertBytes = mod.Import(typeof(ConstUtility).GetMethod("GetBytes", new[] { typeof(byte[]), typeof(int), typeof(int) }));
|
||||
}
|
||||
|
||||
IMethod GetConvertMethod(ModuleDef mod)
|
||||
{
|
||||
InitImportMetadatas(mod);
|
||||
switch (Type)
|
||||
{
|
||||
case DataNodeType.Int32: return s_convertInt;
|
||||
case DataNodeType.Int64: return s_convertLong;
|
||||
case DataNodeType.Float32: return s_convertFloat;
|
||||
case DataNodeType.Float64: return s_convertDouble;
|
||||
case DataNodeType.String: return s_convertString;
|
||||
case DataNodeType.Bytes: return s_convertBytes;
|
||||
default: throw new NotSupportedException($"Unsupported type: {Type}.");
|
||||
}
|
||||
}
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
// only support Int32, int64, bytes.
|
||||
// string can only create from StringFromBytesNode
|
||||
// x = memcpy array.GetRange(index, length);
|
||||
var output = ctx.output;
|
||||
RvaData rvaData = AllocateRvaData(ctx);
|
||||
ModuleDef mod = ctx.method.Module;
|
||||
IMethod convertMethod = GetConvertMethod(mod);
|
||||
switch (Type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
case DataNodeType.Int64:
|
||||
case DataNodeType.Float32:
|
||||
case DataNodeType.Float64:
|
||||
{
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Ldsfld, rvaData.field));
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.offset));
|
||||
output.Add(Instruction.Create(OpCodes.Call, convertMethod));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.String:
|
||||
case DataNodeType.Bytes:
|
||||
{
|
||||
|
||||
// Encoding.UTF8.GetString(data, offset, length);
|
||||
//ctx.output.Add(Instruction.Create(OpCodes.Ldsfld, s_Encoding_Utf8));
|
||||
//ctx.output.Add(Instruction.Create(OpCodes.Ldsfld, rvaData.field));
|
||||
//output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.offset));
|
||||
//output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.size));
|
||||
//output.Add(Instruction.Create(OpCodes.Call, convertMethod));
|
||||
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Ldsfld, rvaData.field));
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.offset));
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, rvaData.size));
|
||||
output.Add(Instruction.Create(OpCodes.Call, convertMethod));
|
||||
break;
|
||||
}
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {Type}.");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public abstract class DataNodeBase : IDataNode
|
||||
{
|
||||
public DataNodeType Type { get; set; }
|
||||
|
||||
public abstract object Value { get; set; }
|
||||
|
||||
public int IntValue => (int)Value;
|
||||
|
||||
public long LongValue => (long) Value;
|
||||
|
||||
public float FloatValue => (float)Value;
|
||||
|
||||
public double DoubleValue => (double)Value;
|
||||
|
||||
public string StringValue => (string)Value;
|
||||
|
||||
public byte[] BytesValue => (byte[])Value;
|
||||
|
||||
public virtual void Init(CreateExpressionOptions options)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public abstract void Compile(CompileContext ctx);
|
||||
}
|
||||
|
||||
|
||||
public abstract class DataNodeBase<T> : DataNodeBase
|
||||
{
|
||||
public T Value2 { get; set; }
|
||||
|
||||
public override object Value
|
||||
{
|
||||
get => Value2;
|
||||
set => Value2 = (T)value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public abstract class DataNodeAny : DataNodeBase
|
||||
{
|
||||
private object _value;
|
||||
|
||||
public override object Value
|
||||
{
|
||||
get => _value;
|
||||
set => _value = value;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,17 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class RvaBytesNode : DataNodeBase<byte[]>
|
||||
{
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,19 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class StringFromEncryptedBytesNode : DataNodeAny
|
||||
{
|
||||
|
||||
public override void Compile(CompileContext ctx)
|
||||
{
|
||||
// only support Int32, int64, bytes.
|
||||
// string can only create from StringFromBytesNode
|
||||
// x = memcpy array.GetRange(index, length);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -4,7 +4,7 @@ using UnityEngine.Assertions;
|
|||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class DefaultModuleMetadataImporter : ModuleMetadataImporterBase
|
||||
public class DefaultModuleMetadataImporter : GroupByModuleEntityBase
|
||||
{
|
||||
public DefaultModuleMetadataImporter() { }
|
||||
|
||||
|
|
|
@ -1,17 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class BytesInitializeFromFieldRvaDataCreator : NodeCreatorBase
|
||||
{
|
||||
public override IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options)
|
||||
{
|
||||
return new BytesInitializeFromFieldRvaDataNode { Type = type, Value = value };
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,17 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class ConstDataCreator : NodeCreatorBase
|
||||
{
|
||||
public override IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options)
|
||||
{
|
||||
return new ConstDataNode { Type = type, Value = value };
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,16 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class ConstFieldDataCreator : NodeCreatorBase
|
||||
{
|
||||
public override IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options)
|
||||
{
|
||||
return new ConstFieldDataNode { Type = type, Value = value };
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,17 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class ConstFromFieldRvaDataCreator : NodeCreatorBase
|
||||
{
|
||||
public override IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options)
|
||||
{
|
||||
return new ConstFromFieldRvaDataNode { Type = type, Value = value };
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,41 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using NUnit.Framework;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
|
||||
public abstract class FunctionBase : IFunction
|
||||
{
|
||||
|
||||
public abstract void CreateArguments(DataNodeType type, object value, CreateExpressionOptions options, List<ConstValue> args);
|
||||
|
||||
public abstract void CompileSelf(CompileContext ctx, List<IDataNode> inputs, List<Instruction> output);
|
||||
|
||||
public virtual void Compile(CompileContext ctx, List<IDataNode> inputs, ConstValue result)
|
||||
{
|
||||
foreach (var input in inputs)
|
||||
{
|
||||
input.Compile(ctx);
|
||||
}
|
||||
CompileSelf(ctx, inputs, ctx.output);
|
||||
}
|
||||
|
||||
public virtual IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options)
|
||||
{
|
||||
var args = new List<ConstValue>();
|
||||
CreateArguments(type, value, options, args);
|
||||
|
||||
options.depth += 1;
|
||||
var argNodes = new List<IDataNode>();
|
||||
foreach (ConstValue cv in args)
|
||||
{
|
||||
var argNode = options.expressionCreator.CreateRandom(cv.type, cv.value, options);
|
||||
argNodes.Add(argNode);
|
||||
}
|
||||
|
||||
return new ConstExpression(this, args.Select(a => options.expressionCreator.CreateRandom(a.type, a.value, options)).ToList(), new ConstValue(type, value));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,49 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class IntAdd : FunctionBase
|
||||
{
|
||||
|
||||
public override void CreateArguments(DataNodeType type, object v, CreateExpressionOptions options, List<ConstValue> args)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
int value = (int)v;
|
||||
|
||||
int op1 = options.random.NextInt();
|
||||
int op2 = value - op1;
|
||||
args.Add(new ConstValue(DataNodeType.Int32, op1));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, op2));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
long value = (long)v;
|
||||
long op1 = options.random.NextLong();
|
||||
long op2 = value - op1;
|
||||
args.Add(new ConstValue(DataNodeType.Int64, op1));
|
||||
args.Add(new ConstValue(DataNodeType.Int64, op2));
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
throw new NotSupportedException($"Unsupported type: {type}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override void CompileSelf(CompileContext ctx, List<IDataNode> inputs, List<Instruction> output)
|
||||
{
|
||||
output.Add(Instruction.Create(OpCodes.Add));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,73 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using NUnit.Framework;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using static UnityEngine.Networking.UnityWebRequest;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class IntRotateShift : FunctionBase
|
||||
{
|
||||
|
||||
public override void CreateArguments(DataNodeType type, object v, CreateExpressionOptions options, List<ConstValue> args)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
int value = (int)v;
|
||||
|
||||
// (value >> amount) | (value << (32 - amount))
|
||||
// << amount
|
||||
// value = b31 b30 .. b0;
|
||||
int leftShiftAmount = options.random.NextInt(8, 16);
|
||||
uint op1 = (uint)value >> leftShiftAmount;
|
||||
int rightShiftAmount = 32 - leftShiftAmount;
|
||||
uint op2 = (uint)value << rightShiftAmount;
|
||||
Assert.AreEqual((uint)value, (op1 << leftShiftAmount) | (op2 >> rightShiftAmount));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, (int)op1));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, leftShiftAmount));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, (int)op2));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, rightShiftAmount));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
long value = (long)v;
|
||||
int leftShiftAmount = options.random.NextInt(16, 32);
|
||||
ulong op1 = (ulong)value >> leftShiftAmount;
|
||||
int rightShiftAmount = 64 - leftShiftAmount;
|
||||
ulong op2 = (ulong)value << rightShiftAmount;
|
||||
Assert.AreEqual((ulong)value, (op1 << leftShiftAmount) | (op2 >> rightShiftAmount));
|
||||
args.Add(new ConstValue(DataNodeType.Int64, (long)op1));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, leftShiftAmount));
|
||||
args.Add(new ConstValue(DataNodeType.Int64, (long)op2));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, rightShiftAmount));
|
||||
break;
|
||||
}
|
||||
default: throw new NotSupportedException($"Unsupported type {type} for IntRotateShift");
|
||||
}
|
||||
}
|
||||
|
||||
public override void CompileSelf(CompileContext ctx, List<IDataNode> inputs, List<Instruction> output)
|
||||
{
|
||||
output.Add(Instruction.Create(OpCodes.Xor));
|
||||
}
|
||||
|
||||
public override void Compile(CompileContext ctx, List<IDataNode> inputs, ConstValue result)
|
||||
{
|
||||
Assert.AreEqual(inputs.Count, 4);
|
||||
inputs[0].Compile(ctx);
|
||||
inputs[1].Compile(ctx);
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Shl));
|
||||
inputs[2].Compile(ctx);
|
||||
inputs[3].Compile(ctx);
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Shr_Un));
|
||||
ctx.output.Add(Instruction.Create(OpCodes.Or));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,46 +0,0 @@
|
|||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using static UnityEngine.Networking.UnityWebRequest;
|
||||
|
||||
namespace Obfuz.Emit.Functions
|
||||
{
|
||||
public class IntXor : FunctionBase
|
||||
{
|
||||
|
||||
public override void CreateArguments(DataNodeType type, object v, CreateExpressionOptions options, List<ConstValue> args)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
int value = (int)v;
|
||||
int op1 = options.random.NextInt();
|
||||
int op2 = value ^ op1;
|
||||
args.Add(new ConstValue(DataNodeType.Int32, op1));
|
||||
args.Add(new ConstValue(DataNodeType.Int32, op2));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
long value = (long)v;
|
||||
long op1 = options.random.NextLong();
|
||||
long op2 = value ^ op1;
|
||||
args.Add(new ConstValue(DataNodeType.Int64, op1));
|
||||
args.Add(new ConstValue(DataNodeType.Int64, op2));
|
||||
break;
|
||||
}
|
||||
default: throw new NotSupportedException($"Unsupported type {type} for Int32FunctionXor");
|
||||
}
|
||||
}
|
||||
|
||||
public override void CompileSelf(CompileContext ctx, List<IDataNode> inputs, List<Instruction> output)
|
||||
{
|
||||
output.Add(Instruction.Create(OpCodes.Xor));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,76 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
using dnlib.DotNet.Emit;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using Unity.Collections.LowLevel.Unsafe;
|
||||
using UnityEngine.Assertions;
|
||||
|
||||
namespace Obfuz.Emit.DataNodes
|
||||
{
|
||||
public class MemoryCastIntAsFloat : FunctionBase
|
||||
{
|
||||
private static IMethod s_castIntAsFloat;
|
||||
private static IMethod s_castLongAsDouble;
|
||||
|
||||
private void InitMetadatas(ModuleDef mod)
|
||||
{
|
||||
if (s_castIntAsFloat != null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var constUtilityType = typeof(ConstUtility);
|
||||
s_castIntAsFloat = mod.Import(constUtilityType.GetMethod("CastIntAsFloat"));
|
||||
Assert.IsNotNull(s_castIntAsFloat, "CastIntAsFloat not found");
|
||||
s_castLongAsDouble = mod.Import(constUtilityType.GetMethod("CastLongAsDouble"));
|
||||
Assert.IsNotNull(s_castLongAsDouble, "CastLongAsDouble not found");
|
||||
}
|
||||
|
||||
public override void CompileSelf(CompileContext ctx, List<IDataNode> inputs, List<Instruction> output)
|
||||
{
|
||||
Assert.AreEqual(1, inputs.Count);
|
||||
InitMetadatas(ctx.method.Module);
|
||||
switch (inputs[0].Type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
output.Add(Instruction.Create(OpCodes.Call, s_castIntAsFloat));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
output.Add(Instruction.Create(OpCodes.Call, s_castLongAsDouble));
|
||||
break;
|
||||
}
|
||||
default: throw new NotSupportedException($"Unsupported type {inputs[0].Type} for MemoryCastIntAsFloat");
|
||||
}
|
||||
}
|
||||
|
||||
public override void CreateArguments(DataNodeType type, object v, CreateExpressionOptions options, List<ConstValue> args)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Float32:
|
||||
{
|
||||
float value = (float)v;
|
||||
int intValue = ConstUtility.CastFloatAsInt(value);
|
||||
args.Add(new ConstValue(DataNodeType.Int32, intValue));
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Float64:
|
||||
{
|
||||
double value = (double)v;
|
||||
long longValue = ConstUtility.CastDoubleAsLong(value);
|
||||
args.Add(new ConstValue(DataNodeType.Int64, longValue));
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
throw new NotImplementedException($"Type:{type} not implemented");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,14 +0,0 @@
|
|||
using System.Collections.Generic;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public abstract class NodeCreatorBase : IFunction
|
||||
{
|
||||
void IFunction.Compile(CompileContext ctx, List<IDataNode> inputs, ConstValue result)
|
||||
{
|
||||
throw new System.NotSupportedException("This function is not supported in this context.");
|
||||
}
|
||||
|
||||
public abstract IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options);
|
||||
}
|
||||
}
|
|
@ -7,29 +7,29 @@ using System.Threading.Tasks;
|
|||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public interface IModuleEmitManager
|
||||
public interface IGroupByModuleEntity
|
||||
{
|
||||
void Init(ModuleDef mod);
|
||||
}
|
||||
|
||||
public abstract class ModuleEmitManagerBase : IModuleEmitManager
|
||||
public abstract class GroupByModuleEntityBase : IGroupByModuleEntity
|
||||
{
|
||||
public abstract void Init(ModuleDef mod);
|
||||
}
|
||||
|
||||
public class EmitManager
|
||||
public class GroupByModuleManager
|
||||
{
|
||||
public static EmitManager Ins { get; private set; }
|
||||
public static GroupByModuleManager Ins { get; private set; }
|
||||
|
||||
|
||||
private readonly Dictionary<(ModuleDef, Type), IModuleEmitManager> _moduleEmitManagers = new System.Collections.Generic.Dictionary<(ModuleDef, Type), IModuleEmitManager>();
|
||||
private readonly Dictionary<(ModuleDef, Type), IGroupByModuleEntity> _moduleEmitManagers = new Dictionary<(ModuleDef, Type), IGroupByModuleEntity>();
|
||||
|
||||
public static void Reset()
|
||||
{
|
||||
Ins = new EmitManager();
|
||||
Ins = new GroupByModuleManager();
|
||||
}
|
||||
|
||||
public T GetEmitManager<T>(ModuleDef mod, Func<T> creator = null) where T : IModuleEmitManager
|
||||
public T GetEntity<T>(ModuleDef mod, Func<T> creator = null) where T : IGroupByModuleEntity
|
||||
{
|
||||
var key = (mod, typeof(T));
|
||||
if (_moduleEmitManagers.TryGetValue(key, out var emitManager))
|
||||
|
@ -53,7 +53,7 @@ namespace Obfuz.Emit
|
|||
}
|
||||
}
|
||||
|
||||
public List<T> GetEmitManagers<T>() where T: IModuleEmitManager
|
||||
public List<T> GetEntities<T>() where T: IGroupByModuleEntity
|
||||
{
|
||||
var managers = new List<T>();
|
||||
foreach (var kv in _moduleEmitManagers)
|
||||
|
@ -65,5 +65,10 @@ namespace Obfuz.Emit
|
|||
}
|
||||
return managers;
|
||||
}
|
||||
|
||||
public DefaultModuleMetadataImporter GetDefaultModuleMetadataImporter(ModuleDef module)
|
||||
{
|
||||
return GetEntity<DefaultModuleMetadataImporter>(module);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,20 +0,0 @@
|
|||
using System.Linq;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using UnityEditor;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
|
||||
public interface IDataNode
|
||||
{
|
||||
DataNodeType Type { get; }
|
||||
|
||||
object Value { get; }
|
||||
|
||||
void Init(CreateExpressionOptions options);
|
||||
|
||||
void Compile(CompileContext ctx);
|
||||
}
|
||||
}
|
|
@ -1,7 +0,0 @@
|
|||
namespace Obfuz.Emit
|
||||
{
|
||||
public interface IDataNodeCreator
|
||||
{
|
||||
IDataNode CreateRandom(DataNodeType type, object value, CreateExpressionOptions options);
|
||||
}
|
||||
}
|
|
@ -1,12 +0,0 @@
|
|||
using System.Collections.Generic;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public interface IFunction
|
||||
{
|
||||
|
||||
IDataNode CreateExpr(DataNodeType type, object value, CreateExpressionOptions options);
|
||||
|
||||
void Compile(CompileContext ctx, List<IDataNode> inputs, ConstValue result);
|
||||
}
|
||||
}
|
|
@ -1,73 +1,73 @@
|
|||
using dnlib.DotNet;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
//using dnlib.DotNet;
|
||||
//using System;
|
||||
//using System.Collections.Generic;
|
||||
//using System.Linq;
|
||||
//using System.Text;
|
||||
//using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public interface IModuleMetadataImporter
|
||||
{
|
||||
void Init(ModuleDef mod);
|
||||
}
|
||||
//namespace Obfuz.Emit
|
||||
//{
|
||||
// public interface IModuleMetadataImporter
|
||||
// {
|
||||
// void Init(ModuleDef mod);
|
||||
// }
|
||||
|
||||
public abstract class ModuleMetadataImporterBase : IModuleMetadataImporter
|
||||
{
|
||||
public abstract void Init(ModuleDef mod);
|
||||
}
|
||||
// public abstract class ModuleMetadataImporterBase : IModuleMetadataImporter
|
||||
// {
|
||||
// public abstract void Init(ModuleDef mod);
|
||||
// }
|
||||
|
||||
public class MetadataImporter
|
||||
{
|
||||
private readonly Dictionary<(ModuleDef, Type), IModuleMetadataImporter> _customModuleMetadataImporters = new Dictionary<(ModuleDef, Type), IModuleMetadataImporter>();
|
||||
// public class MetadataImporter
|
||||
// {
|
||||
// private readonly Dictionary<(ModuleDef, Type), IModuleMetadataImporter> _customModuleMetadataImporters = new Dictionary<(ModuleDef, Type), IModuleMetadataImporter>();
|
||||
|
||||
public static MetadataImporter Instance { get; private set; }
|
||||
// public static MetadataImporter Instance { get; private set; }
|
||||
|
||||
public static void Reset()
|
||||
{
|
||||
Instance = new MetadataImporter();
|
||||
}
|
||||
// public static void Reset()
|
||||
// {
|
||||
// Instance = new MetadataImporter();
|
||||
// }
|
||||
|
||||
public DefaultModuleMetadataImporter GetDefaultModuleMetadataImporter(ModuleDef module)
|
||||
{
|
||||
return GetCustomModuleMetadataImporter<DefaultModuleMetadataImporter>(module);
|
||||
}
|
||||
// public DefaultModuleMetadataImporter GetDefaultModuleMetadataImporter(ModuleDef module)
|
||||
// {
|
||||
// return GetCustomModuleMetadataImporter<DefaultModuleMetadataImporter>(module);
|
||||
// }
|
||||
|
||||
public List<DefaultModuleMetadataImporter> GetDefaultModuleMetadataImporters()
|
||||
{
|
||||
return GetCustomModuleMetadataImporters<DefaultModuleMetadataImporter>();
|
||||
}
|
||||
// public List<DefaultModuleMetadataImporter> GetDefaultModuleMetadataImporters()
|
||||
// {
|
||||
// return GetCustomModuleMetadataImporters<DefaultModuleMetadataImporter>();
|
||||
// }
|
||||
|
||||
public T GetCustomModuleMetadataImporter<T>(ModuleDef module, Func<ModuleDef, T> creator = null) where T : IModuleMetadataImporter
|
||||
{
|
||||
var key = (module, typeof(T));
|
||||
if (!_customModuleMetadataImporters.TryGetValue(key, out var importer))
|
||||
{
|
||||
if (creator != null)
|
||||
{
|
||||
importer = creator(module);
|
||||
}
|
||||
else
|
||||
{
|
||||
importer = (IModuleMetadataImporter)Activator.CreateInstance(typeof(T));
|
||||
}
|
||||
importer.Init(module);
|
||||
_customModuleMetadataImporters[key] = importer;
|
||||
}
|
||||
return (T)importer;
|
||||
}
|
||||
// public T GetCustomModuleMetadataImporter<T>(ModuleDef module, Func<ModuleDef, T> creator = null) where T : IModuleMetadataImporter
|
||||
// {
|
||||
// var key = (module, typeof(T));
|
||||
// if (!_customModuleMetadataImporters.TryGetValue(key, out var importer))
|
||||
// {
|
||||
// if (creator != null)
|
||||
// {
|
||||
// importer = creator(module);
|
||||
// }
|
||||
// else
|
||||
// {
|
||||
// importer = (IModuleMetadataImporter)Activator.CreateInstance(typeof(T));
|
||||
// }
|
||||
// importer.Init(module);
|
||||
// _customModuleMetadataImporters[key] = importer;
|
||||
// }
|
||||
// return (T)importer;
|
||||
// }
|
||||
|
||||
public List<T> GetCustomModuleMetadataImporters<T>()
|
||||
{
|
||||
var result = new List<T>();
|
||||
foreach (var kvp in _customModuleMetadataImporters)
|
||||
{
|
||||
if (kvp.Key.Item2 == typeof(T))
|
||||
{
|
||||
result.Add((T)kvp.Value);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
// public List<T> GetCustomModuleMetadataImporters<T>()
|
||||
// {
|
||||
// var result = new List<T>();
|
||||
// foreach (var kvp in _customModuleMetadataImporters)
|
||||
// {
|
||||
// if (kvp.Key.Item2 == typeof(T))
|
||||
// {
|
||||
// result.Add((T)kvp.Value);
|
||||
// }
|
||||
// }
|
||||
// return result;
|
||||
// }
|
||||
// }
|
||||
//}
|
||||
|
|
|
@ -1,19 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
[AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = true)]
|
||||
public class NodeOutputAttribute : Attribute
|
||||
{
|
||||
public DataNodeType Type { get; }
|
||||
|
||||
public NodeOutputAttribute(DataNodeType type)
|
||||
{
|
||||
Type = type;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,77 +0,0 @@
|
|||
|
||||
using Obfuz.Utils;
|
||||
using Obfuz.Emit.DataNodes;
|
||||
using Obfuz.Emit.Functions;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class RandomDataNodeCreator : DataNodeCreatorBase
|
||||
{
|
||||
private readonly Dictionary<DataNodeType, List<IFunction>> _functions = new Dictionary<DataNodeType, List<IFunction>>();
|
||||
|
||||
private readonly IRandom _random;
|
||||
|
||||
public RandomDataNodeCreator(IRandom random)
|
||||
{
|
||||
_random = random;
|
||||
var intFuncs = new List<IFunction>()
|
||||
{
|
||||
new IntAdd(),
|
||||
new IntXor(),
|
||||
new IntRotateShift(),
|
||||
//new ConstFromFieldRvaDataCreator(),
|
||||
//new ConstDataCreator(),
|
||||
};
|
||||
_functions.Add(DataNodeType.Int32, intFuncs);
|
||||
_functions.Add(DataNodeType.Int64, intFuncs);
|
||||
|
||||
var floatFuncs = new List<IFunction>()
|
||||
{
|
||||
new MemoryCastIntAsFloat(),
|
||||
};
|
||||
_functions.Add(DataNodeType.Float32, floatFuncs);
|
||||
_functions.Add(DataNodeType.Float64, floatFuncs);
|
||||
|
||||
var stringFuncs = new List<IFunction>()
|
||||
{
|
||||
new ConstFieldDataCreator(),
|
||||
};
|
||||
_functions.Add(DataNodeType.String, stringFuncs);
|
||||
var bytesFuncs = new List<IFunction>()
|
||||
{
|
||||
new BytesInitializeFromFieldRvaDataCreator(),
|
||||
};
|
||||
_functions.Add(DataNodeType.Bytes, bytesFuncs);
|
||||
}
|
||||
|
||||
public override IDataNode CreateRandom(DataNodeType type, object value, CreateExpressionOptions options)
|
||||
{
|
||||
if (!_functions.TryGetValue(type, out var funcs))
|
||||
{
|
||||
throw new System.Exception($"No functions available for type {type}");
|
||||
}
|
||||
if (options.depth >= 2)
|
||||
{
|
||||
//return new ConstDataNode() { Type = type, Value = value };
|
||||
return _random.NextInt(100) < 50 ?
|
||||
//return true ?
|
||||
new ConstFromFieldRvaDataNode() { Type = type, Value = value } :
|
||||
new ConstDataNode() { Type = type, Value = value };
|
||||
}
|
||||
var func = funcs[options.random.NextInt(funcs.Count)];
|
||||
return func.CreateExpr(type, value, options);
|
||||
}
|
||||
|
||||
public IDataNode CreateRandom(DataNodeType type, object value)
|
||||
{
|
||||
var options = new CreateExpressionOptions
|
||||
{
|
||||
depth = 0,
|
||||
random = _random,
|
||||
expressionCreator = this,
|
||||
};
|
||||
return CreateRandom(type, value, options);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,485 +0,0 @@
|
|||
using dnlib.DotNet;
|
||||
using dnlib.DotNet.Emit;
|
||||
using Obfuz.Utils;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using UnityEngine.Assertions;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
{
|
||||
public class EncryptionCompileContext
|
||||
{
|
||||
public ModuleDef module;
|
||||
|
||||
public DefaultModuleMetadataImporter DefaultModuleMetadataImporter => MetadataImporter.Instance.GetDefaultModuleMetadataImporter(module);
|
||||
}
|
||||
|
||||
public interface IVariableTransformer
|
||||
{
|
||||
object Compute(object value);
|
||||
|
||||
object ReverseCompute(object value);
|
||||
|
||||
void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx);
|
||||
|
||||
void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx);
|
||||
}
|
||||
|
||||
public abstract class VariableTransformerBase : IVariableTransformer
|
||||
{
|
||||
public abstract object Compute(object value);
|
||||
public abstract object ReverseCompute(object value);
|
||||
public abstract void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx);
|
||||
public abstract void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx);
|
||||
}
|
||||
|
||||
public class AddVariableTransformer : VariableTransformerBase
|
||||
{
|
||||
private readonly DataNodeType _type;
|
||||
private readonly object _addValue;
|
||||
|
||||
public AddVariableTransformer(DataNodeType type, object addValue)
|
||||
{
|
||||
_type = type;
|
||||
_addValue = addValue;
|
||||
}
|
||||
|
||||
public override object Compute(object value)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
return (int)value + (int)_addValue;
|
||||
case DataNodeType.Int64:
|
||||
return (long)value + (long)_addValue;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public override object ReverseCompute(object value)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
return (int)value - (int)_addValue;
|
||||
case DataNodeType.Int64:
|
||||
return (long)value - (long)_addValue;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, (int)_addValue));
|
||||
output.Add(Instruction.Create(OpCodes.Add));
|
||||
break;
|
||||
case DataNodeType.Int64:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I8, (long)_addValue));
|
||||
output.Add(Instruction.Create(OpCodes.Add));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, -(int)_addValue));
|
||||
output.Add(Instruction.Create(OpCodes.Add));
|
||||
break;
|
||||
case DataNodeType.Int64:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I8, -(long)_addValue));
|
||||
output.Add(Instruction.Create(OpCodes.Add));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public static AddVariableTransformer Create(DataNodeType type, IRandom random)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32: return new AddVariableTransformer(type, random.NextInt());
|
||||
case DataNodeType.Int64: return new AddVariableTransformer(type, random.NextLong());
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {type}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class XorVariableTransformer : VariableTransformerBase
|
||||
{
|
||||
private readonly DataNodeType _type;
|
||||
private readonly object _xorValue;
|
||||
public XorVariableTransformer(DataNodeType type, object xorValue)
|
||||
{
|
||||
_type = type;
|
||||
_xorValue = xorValue;
|
||||
}
|
||||
|
||||
public override object Compute(object value)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
return (int)value ^ (int)_xorValue;
|
||||
case DataNodeType.Int64:
|
||||
return (long)value ^ (long)_xorValue;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public override object ReverseCompute(object value)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
return (int)value ^ (int)_xorValue;
|
||||
case DataNodeType.Int64:
|
||||
return (long)value ^ (long)_xorValue;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, (int)_xorValue));
|
||||
output.Add(Instruction.Create(OpCodes.Xor));
|
||||
break;
|
||||
case DataNodeType.Int64:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I8, (long)_xorValue));
|
||||
output.Add(Instruction.Create(OpCodes.Xor));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I4, (int)_xorValue));
|
||||
output.Add(Instruction.Create(OpCodes.Xor));
|
||||
break;
|
||||
case DataNodeType.Int64:
|
||||
output.Add(Instruction.Create(OpCodes.Ldc_I8, (long)_xorValue));
|
||||
output.Add(Instruction.Create(OpCodes.Xor));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_type}");
|
||||
}
|
||||
}
|
||||
|
||||
public static XorVariableTransformer Create(DataNodeType type, IRandom random)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32: return new XorVariableTransformer(type, random.NextInt());
|
||||
case DataNodeType.Int64: return new XorVariableTransformer(type, random.NextLong());
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {type}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class CastFloatAsIntTransformer : VariableTransformerBase
|
||||
{
|
||||
private readonly DataNodeType _outputType;
|
||||
|
||||
public CastFloatAsIntTransformer(DataNodeType srcType)
|
||||
{
|
||||
switch (srcType)
|
||||
{
|
||||
case DataNodeType.Float32: _outputType = DataNodeType.Int32; break;
|
||||
case DataNodeType.Float64: _outputType = DataNodeType.Int64; break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {srcType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override object Compute(object value)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
return ConstUtility.CastFloatAsInt((float)value);
|
||||
case DataNodeType.Int64:
|
||||
return ConstUtility.CastDoubleAsLong((double)value);
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override object ReverseCompute(object value)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
return ConstUtility.CastIntAsFloat((int)value);
|
||||
case DataNodeType.Int64:
|
||||
return ConstUtility.CastLongAsDouble((long)value);
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastFloatAsInt));
|
||||
break;
|
||||
case DataNodeType.Int64:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastDoubleAsLong));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastIntAsFloat));
|
||||
break;
|
||||
case DataNodeType.Int64:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastLongAsDouble));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public static CastFloatAsIntTransformer Create(DataNodeType type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Float32:
|
||||
case DataNodeType.Float64: return new CastFloatAsIntTransformer(type);
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {type}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class CastIntAsFloatTransformer : VariableTransformerBase
|
||||
{
|
||||
private readonly DataNodeType _outputType;
|
||||
|
||||
public CastIntAsFloatTransformer(DataNodeType srcType)
|
||||
{
|
||||
switch (srcType)
|
||||
{
|
||||
case DataNodeType.Int32: _outputType = DataNodeType.Float32; break;
|
||||
case DataNodeType.Int64: _outputType = DataNodeType.Float64; break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {srcType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override object Compute(object value)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Float32:
|
||||
return ConstUtility.CastIntAsFloat((int)value);
|
||||
case DataNodeType.Float64:
|
||||
return ConstUtility.CastLongAsDouble((long)value);
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override object ReverseCompute(object value)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Float32:
|
||||
return ConstUtility.CastFloatAsInt((float)value);
|
||||
case DataNodeType.Float64:
|
||||
return ConstUtility.CastDoubleAsLong((double)value);
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Float32:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastIntAsFloat));
|
||||
break;
|
||||
case DataNodeType.Float64:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastLongAsDouble));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public override void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
switch (_outputType)
|
||||
{
|
||||
case DataNodeType.Float32:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastFloatAsInt));
|
||||
break;
|
||||
case DataNodeType.Float64:
|
||||
output.Add(Instruction.Create(OpCodes.Call, ctx.DefaultModuleMetadataImporter.CastDoubleAsLong));
|
||||
break;
|
||||
default: throw new NotSupportedException($"Unsupported type: {_outputType}");
|
||||
}
|
||||
}
|
||||
|
||||
public static CastIntAsFloatTransformer Create(DataNodeType type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
case DataNodeType.Int64: return new CastIntAsFloatTransformer(type);
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {type}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class VariableEncryption
|
||||
{
|
||||
private readonly List<IVariableTransformer> _transformers = new List<IVariableTransformer>();
|
||||
|
||||
private readonly DataNodeType _type;
|
||||
|
||||
public VariableEncryption(DataNodeType type, IRandom random)
|
||||
{
|
||||
_type = type;
|
||||
if (type == DataNodeType.Float32)
|
||||
{
|
||||
_transformers.Add(CastFloatAsIntTransformer.Create(type));
|
||||
_transformers.AddRange(CreateTransformers(DataNodeType.Int32, random));
|
||||
_transformers.Add(CastIntAsFloatTransformer.Create(DataNodeType.Int32));
|
||||
|
||||
Assert.AreEqual(1.0f, (float)ComputeValueAfterRevertTransform(ComputeValueAfterTransform(1.0f, _transformers), _transformers));
|
||||
}
|
||||
else if (type == DataNodeType.Float64)
|
||||
{
|
||||
_transformers.Add(CastFloatAsIntTransformer.Create(type));
|
||||
_transformers.AddRange(CreateTransformers(DataNodeType.Int64, random));
|
||||
_transformers.Add(CastIntAsFloatTransformer.Create(DataNodeType.Int64));
|
||||
Assert.AreEqual(1.0, (double)ComputeValueAfterRevertTransform(ComputeValueAfterTransform(1.0, _transformers), _transformers));
|
||||
}
|
||||
else if (type == DataNodeType.Int32)
|
||||
{
|
||||
_transformers.AddRange(CreateTransformers(type, random));
|
||||
Assert.AreEqual(1, (int)ComputeValueAfterRevertTransform(ComputeValueAfterTransform(1, _transformers), _transformers));
|
||||
}
|
||||
else if (type == DataNodeType.Int64)
|
||||
{
|
||||
_transformers.AddRange(CreateTransformers(type, random));
|
||||
Assert.AreEqual(1L, (long)ComputeValueAfterRevertTransform(ComputeValueAfterTransform(1L, _transformers), _transformers));
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new NotSupportedException($"Unsupported type: {type} for VariableEncryption");
|
||||
}
|
||||
}
|
||||
|
||||
private List<IVariableTransformer> CreateTransformers(DataNodeType type, IRandom random)
|
||||
{
|
||||
var output = new List<IVariableTransformer>();
|
||||
output.Add(XorVariableTransformer.Create(type, random));
|
||||
output.Add(AddVariableTransformer.Create(type, random));
|
||||
output.Add(XorVariableTransformer.Create(type, random));
|
||||
//int count = 3;
|
||||
//for (int i = 0; i < count; i++)
|
||||
//{
|
||||
// switch(random.NextInt(2))
|
||||
// {
|
||||
// case 0:
|
||||
// {
|
||||
// var transformer = AddVariableTransformer.Create(type, random);
|
||||
// output.Add(transformer);
|
||||
// break;
|
||||
// }
|
||||
// case 1:
|
||||
// {
|
||||
// var transformer = XorVariableTransformer.Create(type, random);
|
||||
// output.Add(transformer);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
//}
|
||||
AddMapZeroToZeroTransform(type, random, output);
|
||||
return output;
|
||||
}
|
||||
|
||||
public static object ComputeValueAfterTransform(object value, List<IVariableTransformer> transformers)
|
||||
{
|
||||
foreach (var transformer in transformers)
|
||||
{
|
||||
value = transformer.Compute(value);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static object ComputeValueAfterRevertTransform(object value, List<IVariableTransformer> transformers)
|
||||
{
|
||||
for (int i = transformers.Count - 1; i >= 0; i--)
|
||||
{
|
||||
var transformer = transformers[i];
|
||||
value = transformer.ReverseCompute(value);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
|
||||
private void AddMapZeroToZeroTransform(DataNodeType type, IRandom random, List<IVariableTransformer> output)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case DataNodeType.Int32:
|
||||
{
|
||||
int value = (int)ComputeValueAfterTransform(0, output);
|
||||
if (value != 0)
|
||||
{
|
||||
output.Add(new AddVariableTransformer(type, -value));
|
||||
}
|
||||
break;
|
||||
}
|
||||
case DataNodeType.Int64:
|
||||
{
|
||||
long value = (long)ComputeValueAfterTransform(0L, output);
|
||||
if (value != 0)
|
||||
{
|
||||
output.Add(new AddVariableTransformer(type, -value));
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
throw new NotSupportedException($"Unsupported type: {type}");
|
||||
}
|
||||
}
|
||||
|
||||
public void EmitTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
foreach (var transformer in _transformers)
|
||||
{
|
||||
transformer.EmitTransform(output, ctx);
|
||||
}
|
||||
}
|
||||
|
||||
public void EmitRevertTransform(List<Instruction> output, EncryptionCompileContext ctx)
|
||||
{
|
||||
for (int i = _transformers.Count - 1; i >= 0; i--)
|
||||
{
|
||||
var transformer = _transformers[i];
|
||||
transformer.EmitRevertTransform(output, ctx);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -30,7 +30,7 @@ namespace Obfuz.ObfusPasses.CallObfus
|
|||
}
|
||||
}
|
||||
|
||||
class ModuleCallProxyAllocator : IModuleEmitManager
|
||||
class ModuleCallProxyAllocator : IGroupByModuleEntity
|
||||
{
|
||||
private ModuleDef _module;
|
||||
private readonly IRandom _random;
|
||||
|
@ -249,7 +249,7 @@ namespace Obfuz.ObfusPasses.CallObfus
|
|||
|
||||
private ModuleCallProxyAllocator GetModuleAllocator(ModuleDef mod)
|
||||
{
|
||||
return EmitManager.Ins.GetEmitManager<ModuleCallProxyAllocator>(mod, () => new ModuleCallProxyAllocator(_random, _encryptor));
|
||||
return GroupByModuleManager.Ins.GetEntity<ModuleCallProxyAllocator>(mod, () => new ModuleCallProxyAllocator(_random, _encryptor));
|
||||
}
|
||||
|
||||
public ProxyCallMethodData Allocate(ModuleDef mod, IMethod method, bool callVir)
|
||||
|
@ -260,7 +260,7 @@ namespace Obfuz.ObfusPasses.CallObfus
|
|||
|
||||
public void Done()
|
||||
{
|
||||
foreach (var allocator in EmitManager.Ins.GetEmitManagers<ModuleCallProxyAllocator>())
|
||||
foreach (var allocator in GroupByModuleManager.Ins.GetEntities<ModuleCallProxyAllocator>())
|
||||
{
|
||||
allocator.Done();
|
||||
}
|
||||
|
|
|
@ -33,7 +33,7 @@ namespace Obfuz.ObfusPasses.CallObfus
|
|||
|
||||
MethodSig sharedMethodSig = MetaUtil.ToSharedMethodSig(calledMethod.Module.CorLibTypes, MetaUtil.GetInflatedMethodSig(calledMethod));
|
||||
ProxyCallMethodData proxyCallMethodData = _proxyCallAllocator.Allocate(callerMethod.Module, calledMethod, callVir);
|
||||
DefaultModuleMetadataImporter importer = MetadataImporter.Instance.GetDefaultModuleMetadataImporter(callerMethod.Module);
|
||||
DefaultModuleMetadataImporter importer = GroupByModuleManager.Ins.GetDefaultModuleMetadataImporter(callerMethod.Module);
|
||||
|
||||
if (needCacheCall)
|
||||
{
|
||||
|
|
|
@ -37,7 +37,7 @@ namespace Obfuz.ObfusPasses.ConstEncrypt
|
|||
|
||||
private DefaultModuleMetadataImporter GetModuleMetadataImporter(MethodDef method)
|
||||
{
|
||||
return MetadataImporter.Instance.GetDefaultModuleMetadataImporter(method.Module);
|
||||
return GroupByModuleManager.Ins.GetDefaultModuleMetadataImporter(method.Module);
|
||||
}
|
||||
|
||||
public void ObfuscateInt(MethodDef method, bool needCacheValue, int value, List<Instruction> obfuscatedInstructions)
|
||||
|
|
|
@ -23,7 +23,7 @@ namespace Obfuz.ObfusPasses.FieldEncrypt
|
|||
|
||||
private DefaultModuleMetadataImporter GetMetadataImporter(MethodDef method)
|
||||
{
|
||||
return MetadataImporter.Instance.GetDefaultModuleMetadataImporter(method.Module);
|
||||
return GroupByModuleManager.Ins.GetDefaultModuleMetadataImporter(method.Module);
|
||||
}
|
||||
|
||||
class FieldEncryptInfo
|
||||
|
|
|
@ -41,8 +41,7 @@ namespace Obfuz
|
|||
_notObfuscatedAssemblyNamesReferencingObfuscated = notObfuscatedAssemblyNamesReferencingObfuscated;
|
||||
_obfuscatedAssemblyOutputDir = obfuscatedAssemblyOutputDir;
|
||||
|
||||
MetadataImporter.Reset();
|
||||
EmitManager.Reset();
|
||||
GroupByModuleManager.Reset();
|
||||
_assemblyCache = new AssemblyCache(new PathAssemblyResolver(assemblySearchDirs.ToArray()));
|
||||
foreach (var pass in obfuscationPasses)
|
||||
{
|
||||
|
|
|
@ -14,7 +14,7 @@ namespace Obfuz.Utils
|
|||
private const long c = 1013904223;
|
||||
private const long m = 4294967296; // 2^32
|
||||
|
||||
private readonly byte[] _key;
|
||||
private readonly int[] _key;
|
||||
|
||||
private int _nextIndex;
|
||||
|
||||
|
@ -22,10 +22,19 @@ namespace Obfuz.Utils
|
|||
|
||||
public RandomWithKey(byte[] key, int seed)
|
||||
{
|
||||
_key = key;
|
||||
_key = ConvertToIntKey(key);
|
||||
_seed = seed;
|
||||
}
|
||||
|
||||
private static int[] ConvertToIntKey(byte[] key)
|
||||
{
|
||||
// ignore last bytes if not aligned to 4
|
||||
int align4Length = key.Length / 4;
|
||||
int[] intKey = new int[align4Length];
|
||||
Buffer.BlockCopy(key, 0, intKey, 0, align4Length * 4);
|
||||
return intKey;
|
||||
}
|
||||
|
||||
public int NextInt(int min, int max)
|
||||
{
|
||||
return min + NextInt(max - min);
|
||||
|
|
Loading…
Reference in New Issue