Skip to content

Commit 180c2ee

Browse files
authored
Merge 8c8d1ea into 9b8615e
2 parents 9b8615e + 8c8d1ea commit 180c2ee

File tree

6 files changed

+89
-46
lines changed

6 files changed

+89
-46
lines changed

Confuser.Core/CoreComponent.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,9 @@ public class CoreComponent : ConfuserComponent {
3737
/// </summary>
3838
public const string _APIStoreId = "Confuser.APIStore";
3939

40+
public const string SymbolsFileName = "symbols.map";
41+
public const string PasswordFileName = "password";
42+
4043
readonly Marker marker;
4144
readonly ConfuserContext _context;
4245

Confuser.Renamer/AnalyzePhase.cs

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
using System.Collections.Generic;
1+
using System;
2+
using System.Collections.Generic;
3+
using System.IO;
24
using System.Linq;
35
using Confuser.Core;
46
using Confuser.Renamer.Analyzers;
@@ -30,6 +32,7 @@ void ParseParameters(IDnlibDef def, ConfuserContext context, NameService service
3032

3133
protected override void Execute(ConfuserContext context, ProtectionParameters parameters) {
3234
var service = (NameService)context.Registry.GetService<INameService>();
35+
3336
context.Logger.Debug("Building VTables & identifier list...");
3437

3538
foreach (ModuleDef moduleDef in parameters.Targets.OfType<ModuleDef>())
@@ -147,9 +150,22 @@ internal void Analyze(NameService service, ConfuserContext context, ProtectionPa
147150
else if (def is EventDef)
148151
Analyze(service, context, parameters, (EventDef)def);
149152
else if (def is ModuleDef) {
150-
var pass = parameters.GetParameter<string>(context, def, "password", null);
151-
if (pass != null)
152-
service.reversibleRenamer = new ReversibleRenamer(pass);
153+
var generatedPassword = parameters.GetParameter<bool>(context, def, "generatePassword");
154+
var password = parameters.GetParameter<string>(context, def, "password");
155+
if (generatedPassword || password != null) {
156+
var reversibleRenamer = service.reversibleRenamer;
157+
if (reversibleRenamer == null) {
158+
if (generatedPassword) {
159+
password = Guid.NewGuid().ToString();
160+
string dir = context.OutputDirectory;
161+
string path = Path.GetFullPath(Path.Combine(dir, CoreComponent.PasswordFileName));
162+
if (!Directory.Exists(dir))
163+
Directory.CreateDirectory(dir);
164+
File.WriteAllText(path, password);
165+
}
166+
service.reversibleRenamer = new ReversibleRenamer(password);
167+
}
168+
}
153169
service.SetCanRename(def, false);
154170
}
155171

Confuser.Renamer/NameProtection.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -61,8 +61,8 @@ protected override void Execute(ConfuserContext context, ProtectionParameters pa
6161
if (map.Count == 0)
6262
return;
6363

64-
string path = Path.GetFullPath(Path.Combine(context.OutputDirectory, "symbols.map"));
65-
string dir = Path.GetDirectoryName(path);
64+
string dir = context.OutputDirectory;
65+
string path = Path.GetFullPath(Path.Combine(dir, CoreComponent.SymbolsFileName));
6666
if (!Directory.Exists(dir))
6767
Directory.CreateDirectory(dir);
6868

Confuser.Renamer/ReversibleRenamer.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,11 @@
55

66
namespace Confuser.Renamer {
77
public class ReversibleRenamer {
8-
readonly RijndaelManaged cipher;
8+
readonly AesManaged cipher;
99
readonly byte[] key;
1010

1111
public ReversibleRenamer(string password) {
12-
cipher = new RijndaelManaged();
12+
cipher = new AesManaged();
1313
using (var sha = SHA256.Create())
1414
cipher.Key = key = sha.ComputeHash(Encoding.UTF8.GetBytes(password));
1515
}

Tests/Confuser.UnitTest/TestBase.cs

Lines changed: 13 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -24,10 +24,10 @@ protected TestBase(ITestOutputHelper outputHelper) =>
2424
protected Task Run(string inputFileName, string[] expectedOutput, SettingItem<Protection> protection,
2525
string outputDirSuffix = "", Action<string> outputAction = null, SettingItem<Packer> packer = null,
2626
Action<ProjectModule> projectModuleAction = null, Func<string, Task> postProcessAction = null,
27-
string seed = null) =>
27+
string seed = null, bool checkOutput = true) =>
2828

2929
Run(new[] { inputFileName }, expectedOutput, protection, outputDirSuffix, outputAction, packer,
30-
projectModuleAction, postProcessAction, seed);
30+
projectModuleAction, postProcessAction, seed, checkOutput);
3131

3232
protected Task Run(string inputFileName, string[] expectedOutput, IEnumerable<SettingItem<Protection>> protections,
3333
string outputDirSuffix = "", Action<string> outputAction = null, SettingItem<Packer> packer = null,
@@ -39,15 +39,15 @@ protected Task Run(string inputFileName, string[] expectedOutput, IEnumerable<Se
3939
protected Task Run(string[] inputFileNames, string[] expectedOutput, SettingItem<Protection> protection,
4040
string outputDirSuffix = "", Action<string> outputAction = null, SettingItem<Packer> packer = null,
4141
Action<ProjectModule> projectModuleAction = null, Func<string, Task> postProcessAction = null,
42-
string seed = null) {
42+
string seed = null, bool checkOutput = true) {
4343
var protections = (protection is null) ? Enumerable.Empty<SettingItem<Protection>>() : new[] { protection };
44-
return Run(inputFileNames, expectedOutput, protections, outputDirSuffix, outputAction, packer, projectModuleAction, postProcessAction, seed);
44+
return Run(inputFileNames, expectedOutput, protections, outputDirSuffix, outputAction, packer, projectModuleAction, postProcessAction, seed, checkOutput);
4545
}
4646

4747
protected async Task Run(string[] inputFileNames, string[] expectedOutput, IEnumerable<SettingItem<Protection>> protections,
4848
string outputDirSuffix = "", Action<string> outputAction = null, SettingItem<Packer> packer = null,
4949
Action<ProjectModule> projectModuleAction = null, Func<string, Task> postProcessAction = null,
50-
string seed = null) {
50+
string seed = null, bool checkOutput = true) {
5151

5252
var baseDir = Environment.CurrentDirectory;
5353
var outputDir = Path.Combine(baseDir, "obfuscated" + outputDirSuffix);
@@ -120,14 +120,16 @@ protected async Task Run(string[] inputFileNames, string[] expectedOutput, IEnum
120120
using (var process = Process.Start(info)) {
121121
using (var stdout = process.StandardOutput) {
122122
try {
123-
Assert.Equal("START", await stdout.ReadLineAsync());
123+
if (checkOutput) {
124+
Assert.Equal("START", await stdout.ReadLineAsync());
124125

125-
foreach (string line in expectedOutput) {
126-
Assert.Equal(line, await stdout.ReadLineAsync());
127-
}
126+
foreach (string line in expectedOutput) {
127+
Assert.Equal(line, await stdout.ReadLineAsync());
128+
}
128129

129-
Assert.Equal("END", await stdout.ReadLineAsync());
130-
Assert.Empty(await stdout.ReadToEndAsync());
130+
Assert.Equal("END", await stdout.ReadLineAsync());
131+
Assert.Empty(await stdout.ReadToEndAsync());
132+
}
131133
}
132134
catch (XunitException) {
133135
try {

Tests/MessageDeobfuscation.Test/MessageDeobfuscationTest.cs

Lines changed: 49 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ public class MessageDeobfuscationTest : TestBase {
1515
"Exception",
1616
" at MessageDeobfuscation.Class.NestedClass.Method(String )",
1717
" at MessageDeobfuscation.Program.Main()");
18+
readonly string _password = "password";
1819

1920
public MessageDeobfuscationTest(ITestOutputHelper outputHelper) : base(outputHelper) { }
2021

@@ -96,6 +97,23 @@ public static IEnumerable<object[]> RenameModeAndExpectedObfuscatedOutput() =>
9697
}
9798
};
9899

100+
[Fact]
101+
[Trait("Category", "Protection")]
102+
public async Task CheckRandomPassword() {
103+
string actualPassword1 = null, actualPassword2 = null;
104+
await RunDeobfuscationWithPassword(true, "0", Array.Empty<string>(), outputPath => {
105+
actualPassword1 = File.ReadAllText(Path.Combine(outputPath, CoreComponent.PasswordFileName));
106+
Assert.True(Guid.TryParse(actualPassword1, out _));
107+
return Task.Delay(0);
108+
});
109+
await RunDeobfuscationWithPassword(true, "1", Array.Empty<string>(), outputPath => {
110+
actualPassword2 = File.ReadAllText(Path.Combine(outputPath, CoreComponent.PasswordFileName));
111+
Assert.True(Guid.TryParse(actualPassword2, out _));
112+
return Task.Delay(0);
113+
});
114+
Assert.NotEqual(actualPassword1, actualPassword2);
115+
}
116+
99117
[Fact]
100118
[Trait("Category", "Protection")]
101119
[Trait("Protection", "rename")]
@@ -105,36 +123,40 @@ public async Task MessageDeobfuscationWithPassword() {
105123
" at oQmpV$y2k2b9P3d6GP1cxGPuRtKaNIZvZcKpZXSfKFG8.CE8t0VDPQk9$jgv1XuRwt1k.FhsPrCLqIAaPKe7abGklvY4(String )",
106124
" at EbUjRcrC76NnA7RJlhQffrfp$vMGHdDfqtVFtWrAOPyD.xgIw9voebB21PlxPFA_hs60()"
107125
};
108-
string password = "password";
109-
await Run(
110-
"MessageDeobfuscation.exe",
111-
expectedObfuscatedOutput,
112-
new SettingItem<Protection>("rename") {
113-
["mode"] = "reversible",
114-
["password"] = password,
115-
["renPdb"] = "true"
116-
},
117-
"Password",
118-
postProcessAction: outputPath => {
119-
var deobfuscator = new MessageDeobfuscator(password);
120-
var deobfuscatedMessage = deobfuscator.DeobfuscateMessage(string.Join(Environment.NewLine, expectedObfuscatedOutput));
126+
await RunDeobfuscationWithPassword(false, "", expectedObfuscatedOutput, outputPath => {
127+
var deobfuscator = new MessageDeobfuscator(_password);
128+
var deobfuscatedMessage =
129+
deobfuscator.DeobfuscateMessage(string.Join(Environment.NewLine, expectedObfuscatedOutput));
121130

122-
void CheckName(string expectedName, string obfuscatedName) {
123-
var name = deobfuscator.DeobfuscateSymbol(obfuscatedName, true);
124-
Assert.Equal(expectedName, name);
125-
}
131+
void CheckName(string expectedName, string obfuscatedName) {
132+
var name = deobfuscator.DeobfuscateSymbol(obfuscatedName, true);
133+
Assert.Equal(expectedName, name);
134+
}
126135

127-
CheckName("MessageDeobfuscation.Class", "oQmpV$y2k2b9P3d6GP1cxGPuRtKaNIZvZcKpZXSfKFG8");
128-
CheckName("NestedClass", "CE8t0VDPQk9$jgv1XuRwt1k");
129-
CheckName("Method", "jevJU4p4yNrAYGqN7GkRWaI");
130-
CheckName("Field", "3IS4xsnUsvDQZop6e4WmNVw");
131-
CheckName("Property", "917VMBMNYHd0kfnnNkgeJ10");
132-
CheckName("Event", "AIyINk7kgFLFc73Md8Nu8Z0");
136+
CheckName("MessageDeobfuscation.Class", "oQmpV$y2k2b9P3d6GP1cxGPuRtKaNIZvZcKpZXSfKFG8");
137+
CheckName("NestedClass", "CE8t0VDPQk9$jgv1XuRwt1k");
138+
CheckName("Method", "jevJU4p4yNrAYGqN7GkRWaI");
139+
CheckName("Field", "3IS4xsnUsvDQZop6e4WmNVw");
140+
CheckName("Property", "917VMBMNYHd0kfnnNkgeJ10");
141+
CheckName("Event", "AIyINk7kgFLFc73Md8Nu8Z0");
133142

134-
Assert.Equal(_expectedDeobfuscatedOutput, deobfuscatedMessage);
135-
return Task.Delay(0);
136-
}
137-
);
143+
Assert.Equal(_expectedDeobfuscatedOutput, deobfuscatedMessage);
144+
return Task.Delay(0);
145+
});
138146
}
147+
148+
async Task RunDeobfuscationWithPassword(bool generatePassword, string suffix, string[] expectedObfuscatedOutput, Func<string, Task> postProcessAction) => await Run(
149+
"MessageDeobfuscation.exe",
150+
expectedObfuscatedOutput,
151+
new SettingItem<Protection>("rename") {
152+
["mode"] = "reversible",
153+
["password"] = _password,
154+
["generatePassword"] = generatePassword.ToString(),
155+
["renPdb"] = "true",
156+
},
157+
$"Password_{(generatePassword ? $"Random{suffix}" : $"Hardcoded{suffix}")}",
158+
checkOutput: !generatePassword,
159+
postProcessAction: postProcessAction
160+
);
139161
}
140162
}

0 commit comments

Comments
 (0)