From 08905b1747fdae6588a0a9a4c07963aa0b7792fc Mon Sep 17 00:00:00 2001 From: VollRahm Date: Tue, 23 Feb 2021 18:22:59 +0100 Subject: [PATCH] - Created apphost-extract-v2 --- src/apphost-extract/TestProject/Program.cs | 14 ++++ .../TestProject/TestProject.csproj | 8 ++ .../apphost-extract-v2/Analyzer.cs | 43 +++++++++++ src/apphost-extract/apphost-extract-v2/Log.cs | 57 ++++++++++++++ .../apphost-extract-v2/Models/IApphostFile.cs | 11 +++ .../apphost-extract-v2/Program.cs | 75 +++++++++++++++++++ .../apphost-extract-v2/Util.cs | 43 +++++++++++ .../apphost-extract-v2.csproj | 9 +++ src/apphost-extract/apphost-extract.sln | 14 +++- .../apphost-extract/AppHostFile.cs | 47 +++++++++++- .../apphost-extract/Program.cs | 6 +- .../Properties/launchSettings.json | 8 ++ .../apphost-extract/apphost-extract.csproj | 2 +- 13 files changed, 331 insertions(+), 6 deletions(-) create mode 100644 src/apphost-extract/TestProject/Program.cs create mode 100644 src/apphost-extract/TestProject/TestProject.csproj create mode 100644 src/apphost-extract/apphost-extract-v2/Analyzer.cs create mode 100644 src/apphost-extract/apphost-extract-v2/Log.cs create mode 100644 src/apphost-extract/apphost-extract-v2/Models/IApphostFile.cs create mode 100644 src/apphost-extract/apphost-extract-v2/Program.cs create mode 100644 src/apphost-extract/apphost-extract-v2/Util.cs create mode 100644 src/apphost-extract/apphost-extract-v2/apphost-extract-v2.csproj create mode 100644 src/apphost-extract/apphost-extract/Properties/launchSettings.json diff --git a/src/apphost-extract/TestProject/Program.cs b/src/apphost-extract/TestProject/Program.cs new file mode 100644 index 0000000..398757b --- /dev/null +++ b/src/apphost-extract/TestProject/Program.cs @@ -0,0 +1,14 @@ +using System; + +namespace TestProject +{ + class Program + { + static void Main(string[] args) + { + Console.WriteLine("Hello World!"); + Console.ReadLine(); + } + + } +} diff --git a/src/apphost-extract/TestProject/TestProject.csproj b/src/apphost-extract/TestProject/TestProject.csproj new file mode 100644 index 0000000..2082704 --- /dev/null +++ b/src/apphost-extract/TestProject/TestProject.csproj @@ -0,0 +1,8 @@ + + + + Exe + net5.0 + + + diff --git a/src/apphost-extract/apphost-extract-v2/Analyzer.cs b/src/apphost-extract/apphost-extract-v2/Analyzer.cs new file mode 100644 index 0000000..5bacd80 --- /dev/null +++ b/src/apphost-extract/apphost-extract-v2/Analyzer.cs @@ -0,0 +1,43 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Reflection.PortableExecutable; +using System.Text; + +namespace apphost_extract_v2 +{ + public class Analyzer + { + private FileStream File; + public PEHeaders PEHeader; + + private readonly byte[] VERSION_SIGNATURE = new byte[] { }; + private const string VERSION_SIGNATURE_MASK = ""; + + public Analyzer(FileStream fs) + { + File = fs; + PEHeader = new PEHeaders(fs); + } + + public SectionHeader GetSegment(string name) + { + var section = PEHeader.SectionHeaders.Where(x => x.Name == name).FirstOrDefault(); + return section; + } + + public ApphostVersion GetVersion() + { + + } + + } + + public enum ApphostVersion + { + NET30, + NET31, + NET5 + } +} diff --git a/src/apphost-extract/apphost-extract-v2/Log.cs b/src/apphost-extract/apphost-extract-v2/Log.cs new file mode 100644 index 0000000..fee114e --- /dev/null +++ b/src/apphost-extract/apphost-extract-v2/Log.cs @@ -0,0 +1,57 @@ +using System; + +public static class Log +{ + public static void Critical(object value) + { + Color(ConsoleColor.Magenta); + Console.WriteLine("[!] " + value.ToString()); + Color(); + } + + public static void Info(object value) + { + Color(ConsoleColor.Cyan); + Console.WriteLine("[+] " + value.ToString()); + } + + public static bool QueryYesNo(string question) + { + var input = QueryString(question); + if (input.ToLower().StartsWith("y")) return true; + else return false; + } + + public static string QueryString(string question) + { + Color(ConsoleColor.Yellow); + Console.Write("[?] " + question); + Color(); + return Console.ReadLine(); + } + + public static void Info(object value, ConsoleColor color) + { + Color(color); + Console.WriteLine("[+] " + value.ToString()); + } + + public static void Error(object value) + { + Color(ConsoleColor.Red); + Console.WriteLine("[-] " + value.ToString()); + Color(); + } + + public static void Fatal(object value) + { + Error(value); + Console.ReadLine(); + Environment.Exit(0); + } + + private static void Color(ConsoleColor color = ConsoleColor.White) + { + Console.ForegroundColor = color; + } +} diff --git a/src/apphost-extract/apphost-extract-v2/Models/IApphostFile.cs b/src/apphost-extract/apphost-extract-v2/Models/IApphostFile.cs new file mode 100644 index 0000000..7dd77c1 --- /dev/null +++ b/src/apphost-extract/apphost-extract-v2/Models/IApphostFile.cs @@ -0,0 +1,11 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace apphost_extract_v2.Models +{ + public interface IApphostFile + { + + } +} diff --git a/src/apphost-extract/apphost-extract-v2/Program.cs b/src/apphost-extract/apphost-extract-v2/Program.cs new file mode 100644 index 0000000..052b3c3 --- /dev/null +++ b/src/apphost-extract/apphost-extract-v2/Program.cs @@ -0,0 +1,75 @@ +using System; +using System.Diagnostics; +using System.IO; +using System.IO.MemoryMappedFiles; +using System.Reflection; + +namespace apphost_extract_v2 +{ + class Program + { + static void Main(string[] args) + { + var file = "net31-fd.exe"; + var fs = new FileStream(file, FileMode.Open, FileAccess.Read); + + var d = new Analyzer(fs).GetTextSectionVA(); + var pattern = new byte[] { 0x4c, 0x8D, 0x5, 0xE2, 0x8A, 0x00, 0x00 }; + string mask = "xxxxxxx"; + + Log.Info("Scanning for pattern..."); + Stopwatch sw = Stopwatch.StartNew(); + var res = Util.PatternScan(fs, 0, (int)fs.Length, pattern, mask); + sw.Stop(); + Log.Info("Found pattern at " + res[0].ToString("X8") + $" in {sw.ElapsedMilliseconds}ms"); + + + + /* Log.Info("apphost-extract by VollRagm\n", ConsoleColor.Yellow); + var path = GetPath(args); + + // var file = AppHostFile.Open(path2);//path.FullName); + // Log.Info($"{file.Header.Manifest.FileEntries.Count} embedded file(s) found."); + + var directory = Path.Combine(path.DirectoryName, path.Name.Remove(path.Name.Length - path.Extension.Length) + "_extracted"); + Console.WriteLine(); + Log.Info("Extracting..."); + + //file.ExtractAll(directory); + + Console.WriteLine(); + Log.Info("Done."); + // file.Close(); + Console.ReadLine();*/ + } + + static FileInfo GetPath(string[] args) + { + try + { + var fileName = new FileInfo(Assembly.GetExecutingAssembly().Location).Name; + + if (args.Length > 0) + { + if (File.Exists(args[0])) + { + return new FileInfo(args[0]); + } + else + { + Log.Fatal($"{args[0]} could not be found. Usage: {fileName} "); + } + } + else + { + Log.Fatal($"No File provided. Usage: {fileName} "); + } + } + catch (Exception ex) + { + Log.Fatal($"Could not get file: {ex.Message}"); + } + return null; + } + } +} diff --git a/src/apphost-extract/apphost-extract-v2/Util.cs b/src/apphost-extract/apphost-extract-v2/Util.cs new file mode 100644 index 0000000..4a04083 --- /dev/null +++ b/src/apphost-extract/apphost-extract-v2/Util.cs @@ -0,0 +1,43 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Text; + +namespace apphost_extract_v2 +{ + public static class Util + { + public static int[] PatternScan(FileStream fs, int start, int length, byte[] pattern, string mask) + { + byte[] scanBuffer = new byte[length]; + fs.Seek(start, SeekOrigin.Begin); + fs.Read(scanBuffer, 0, length); + + List scanResults = new List(); + + for(int i = 0; i < scanBuffer.Length - pattern.Length; i++) + { + if (!IsMatch(scanBuffer, i, pattern, mask)) + continue; + + scanResults.Add(start + i); + } + + return scanResults.ToArray(); + } + + + //https://stackoverflow.com/a/283648/10724593 + private static bool IsMatch(byte[] array, int position, byte[] candidate, string mask) + { + if (candidate.Length > (array.Length - position)) + return false; + + for (int i = 0; i < candidate.Length; i++) + if (mask[i] == 'x' && array[position + i] != candidate[i]) + return false; + + return true; + } + } +} diff --git a/src/apphost-extract/apphost-extract-v2/apphost-extract-v2.csproj b/src/apphost-extract/apphost-extract-v2/apphost-extract-v2.csproj new file mode 100644 index 0000000..119f455 --- /dev/null +++ b/src/apphost-extract/apphost-extract-v2/apphost-extract-v2.csproj @@ -0,0 +1,9 @@ + + + + Exe + netcoreapp3.1 + apphost_extract_v2 + + + diff --git a/src/apphost-extract/apphost-extract.sln b/src/apphost-extract/apphost-extract.sln index 76f7aab..420d758 100644 --- a/src/apphost-extract/apphost-extract.sln +++ b/src/apphost-extract/apphost-extract.sln @@ -3,7 +3,11 @@ Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio Version 16 VisualStudioVersion = 16.0.30204.135 MinimumVisualStudioVersion = 10.0.40219.1 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "apphost-extract", "apphost-extract\apphost-extract.csproj", "{150E6D0D-598E-40E7-B7DD-3941F31E5C63}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "apphost-extract", "apphost-extract\apphost-extract.csproj", "{150E6D0D-598E-40E7-B7DD-3941F31E5C63}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TestProject", "TestProject\TestProject.csproj", "{35EC6BD7-EAA9-4898-BC0F-0D3F1F40E911}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "apphost-extract-v2", "apphost-extract-v2\apphost-extract-v2.csproj", "{5BEE71B9-BBDE-4C45-BE03-640119A2DC04}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution @@ -15,6 +19,14 @@ Global {150E6D0D-598E-40E7-B7DD-3941F31E5C63}.Debug|Any CPU.Build.0 = Debug|Any CPU {150E6D0D-598E-40E7-B7DD-3941F31E5C63}.Release|Any CPU.ActiveCfg = Release|Any CPU {150E6D0D-598E-40E7-B7DD-3941F31E5C63}.Release|Any CPU.Build.0 = Release|Any CPU + {35EC6BD7-EAA9-4898-BC0F-0D3F1F40E911}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {35EC6BD7-EAA9-4898-BC0F-0D3F1F40E911}.Debug|Any CPU.Build.0 = Debug|Any CPU + {35EC6BD7-EAA9-4898-BC0F-0D3F1F40E911}.Release|Any CPU.ActiveCfg = Release|Any CPU + {35EC6BD7-EAA9-4898-BC0F-0D3F1F40E911}.Release|Any CPU.Build.0 = Release|Any CPU + {5BEE71B9-BBDE-4C45-BE03-640119A2DC04}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {5BEE71B9-BBDE-4C45-BE03-640119A2DC04}.Debug|Any CPU.Build.0 = Debug|Any CPU + {5BEE71B9-BBDE-4C45-BE03-640119A2DC04}.Release|Any CPU.ActiveCfg = Release|Any CPU + {5BEE71B9-BBDE-4C45-BE03-640119A2DC04}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/src/apphost-extract/apphost-extract/AppHostFile.cs b/src/apphost-extract/apphost-extract/AppHostFile.cs index ea96e5d..f269262 100644 --- a/src/apphost-extract/apphost-extract/AppHostFile.cs +++ b/src/apphost-extract/apphost-extract/AppHostFile.cs @@ -2,6 +2,7 @@ using System.Collections.Generic; using System.IO; using System.Linq; +using System.Reflection.PortableExecutable; using System.Text; using System.Threading.Tasks; @@ -12,18 +13,33 @@ namespace apphost_extract private FileStream FileStream; public AppHostFileHeader Header { get; set; } + private ApphostVersion Version { get; set; } - private const int HEADER_OFFSET_PTR = 0x27600; + private const int VERSION_OFFSET_NET3 = 0x1A3E8; + + private const int HEADER_OFFSET_PTR_NET5 = 0x8E508; + private const int HEADER_OFFSET_PTR_NET3 = 0x27600; + + public AppHostFile(FileStream fileStream) { FileStream = fileStream; - var headerVA = GetHeaderAddress(HEADER_OFFSET_PTR); - + //RDATA = GetRDATASection(fileStream); + var ver = GetVersion(VERSION_OFFSET_NET3); + var headerVA = GetHeaderAddress(HEADER_OFFSET_PTR_NET3); + Header = new AppHostFileHeader(FileStream, headerVA); } + private int GetRDATASection(FileStream fileStream) + { + var pefile = new PEReader(fileStream); + var sectionHeaders = pefile.PEHeaders.SectionHeaders; + return sectionHeaders.Where(header => header.Name == ".rdata").FirstOrDefault().VirtualAddress + 0x668; + } + public int GetHeaderAddress(int offset) { var buffer = new byte[16]; @@ -32,6 +48,25 @@ namespace apphost_extract return BitConverter.ToInt32(buffer, 0); } + public ApphostVersion GetVersion(int offset) + { + FileStream.Seek(offset, SeekOrigin.Begin); + var buffer = new byte[10]; + FileStream.Read(buffer, 0, buffer.Length); + var versionStr = Encoding.Unicode.GetString(buffer); + + if (versionStr.StartsWith("3.")) + { + Log.Info("Detected .NET Core 3."); + return ApphostVersion.NET3; + } + else + { + Log.Info("Could not detect .NET Core version, assumming .NET Core 5."); + return ApphostVersion.NET5; + } + } + public static AppHostFile Open(string path) { @@ -77,4 +112,10 @@ namespace apphost_extract FileStream.Close(); } } + + public enum ApphostVersion + { + NET5, + NET3 + } } diff --git a/src/apphost-extract/apphost-extract/Program.cs b/src/apphost-extract/apphost-extract/Program.cs index a051046..1f5ffce 100644 --- a/src/apphost-extract/apphost-extract/Program.cs +++ b/src/apphost-extract/apphost-extract/Program.cs @@ -14,7 +14,11 @@ namespace apphost_extract { Log.Info("apphost-extract by VollRagm\n", ConsoleColor.Yellow); var path = GetPath(args); - var file = AppHostFile.Open(path.FullName); + + var path2 = "test.exe"; + //var path2 = "AmongUsUnlocker.exe"; + + var file = AppHostFile.Open(path2);//path.FullName); Log.Info($"{file.Header.Manifest.FileEntries.Count} embedded file(s) found."); var directory = Path.Combine(path.DirectoryName, path.Name.Remove(path.Name.Length - path.Extension.Length) +"_extracted"); diff --git a/src/apphost-extract/apphost-extract/Properties/launchSettings.json b/src/apphost-extract/apphost-extract/Properties/launchSettings.json new file mode 100644 index 0000000..bf6c7e4 --- /dev/null +++ b/src/apphost-extract/apphost-extract/Properties/launchSettings.json @@ -0,0 +1,8 @@ +{ + "profiles": { + "apphost-extract": { + "commandName": "Project", + "commandLineArgs": "AmongUsUnlocker.exe" + } + } +} \ No newline at end of file diff --git a/src/apphost-extract/apphost-extract/apphost-extract.csproj b/src/apphost-extract/apphost-extract/apphost-extract.csproj index 306585f..c7a35cc 100644 --- a/src/apphost-extract/apphost-extract/apphost-extract.csproj +++ b/src/apphost-extract/apphost-extract/apphost-extract.csproj @@ -1,6 +1,6 @@  - net5.0 + netcoreapp3.1 Exe apphost_extract false