Exemplo n.º 1
0
        private IEnumerable <T> Assmeble <T>(AssemblySource <MASM> assemblySource, TargetArch targetArch, Func <byte[], T> TConstructor)
            where T : ObjectFile, new()
        {
            List <T> objectFiles = new List <T>();

            using (new TemporaryContext())
            {
                foreach (var sourceFile in assemblySource.SourceFiles)
                {
                    System.IO.File.WriteAllBytes(sourceFile.Filename, sourceFile.Bytes);
                }
                foreach (var sourceFile in assemblySource.SourceFiles.Where(sf => sf.Type == AssemblySourceFileType.Asm))
                {
                    var program         = targetArch == TargetArch.x64 ? "ml64.exe" : "ml.exe";
                    var arguments       = String.Format("/nologo /Fo object.obj /c /Cx {0}", sourceFile.Filename);
                    var assembleCommand = program + " " + arguments;
                    var msvcVersion     = version.ToString().Replace("v", "").Replace("_", ".");
                    var assembleBatFile = @"call ""C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\VCVARSALL.bat"" {0} -vcvars_ver=" + msvcVersion + "\r\n" + assembleCommand;
                    assembleBatFile = String.Format(assembleBatFile, targetArch.ToString());
                    File.WriteAllText("assemble.bat", assembleBatFile);
                    var proc = Process.Start("cmd.exe", "/c " + "assemble.bat");
                    proc.WaitForExit();
                    if (!System.IO.File.Exists("object.obj"))
                    {
                        throw new Exception("Masm error. Object file not found.");
                    }
                    var objectFileBytes = System.IO.File.ReadAllBytes("object.obj");
                    objectFiles.Add(TConstructor(objectFileBytes));
                }
            }
            return(objectFiles);
        }
Exemplo n.º 2
0
        public static IntPtr GetDisasm(Machine machine)
        {
            TargetArch target = TargetArch.Target_Host;

            switch (machine)
            {
            case Machine.Amd64:
                target = TargetArch.Target_X64;
                break;

            case Machine.I386:
                target = TargetArch.Target_X86;
                break;

            case Machine.Arm64:
                target = TargetArch.Target_Arm64;
                break;

            case Machine.ArmThumb2:
                target = TargetArch.Target_Thumb;
                break;

            default:
                R2RDump.WriteWarning($"{machine} not supported on CoreDisTools");
                return(IntPtr.Zero);
            }
            return(InitBufferedDisasm(target));
        }
Exemplo n.º 3
0
            static Executable ShellcodeToExe(IShellcode shellcode, TargetArch targetArch)
            {
                switch (targetArch)
                {
                case TargetArch.x64:
                {
                    var rawShellcodeAsm = new RawShellcodeYasmAssemblySource(shellcode, symbolName: "SheSellsShellCodesByTheSilkRoad");
                    var staticLibrary   = ((IAssembler <YASM, Win64ObjectFile>) new MyWarez.Plugins.Yasm.Yasm()).Assemble(rawShellcodeAsm);
                    var entryPoint      = ((ICFunction)rawShellcodeAsm).Name;
                    var linkerConfig    = new MyWarez.Plugins.GoDevTool.Linker.Config(ENTRY: entryPoint);
                    return(((ILinker <Win64ObjectFile, Executable>) new MyWarez.Plugins.GoDevTool.Linker(linkerConfig)).Link(staticLibrary));
                }

                case TargetArch.x86:
                {
                    var rawShellcodeAsm = new RawShellcodeYasmAssemblySource(shellcode, symbolName: "SheSellsShellCodesByTheSilkRoad");
                    var staticLibrary   = ((IAssembler <YASM, Win32ObjectFile>) new MyWarez.Plugins.Yasm.Yasm()).Assemble(rawShellcodeAsm);
                    var entryPoint      = ((ICFunction)rawShellcodeAsm).Name;
                    var linkerConfig    = new MyWarez.Plugins.GoDevTool.Linker.Config(ENTRY: entryPoint);
                    var exe             = ((ILinker <Win32ObjectFile, Executable>) new MyWarez.Plugins.GoDevTool.Linker(linkerConfig)).Link(staticLibrary);
                    return(exe);
                }

                default:
                    throw new Exception();
                }
            }
Exemplo n.º 4
0
        // TODO: Support compiling source files recursively
        private StaticLibrary <T> Compile <T>(ICCxxSource source, TargetArch targetArch, Func <byte[], T> TConstructor)
            where T : ObjectFile, new()
        {
            switch (targetArch)
            {
            case TargetArch.x86:
                CConfig.MACHINE = Config.Machine.X86;
                break;

            case TargetArch.x64:
                CConfig.MACHINE = Config.Machine.X64;
                break;

            case TargetArch.arm:
            case TargetArch.arm64:
                CConfig.MACHINE = Config.Machine.ARM;
                break;
            }

            using (new TemporaryContext())
            {
                var exts = new HashSet <string>();
                foreach (var sourceFile in source.SourceFiles)
                {
                    File.WriteAllText(sourceFile.Filename, sourceFile.Source);
                    if (sourceFile.Type == CCxxSourceFileType.C || sourceFile.Type == CCxxSourceFileType.Cxx)
                    {
                        exts.Add(Path.GetExtension(sourceFile.Filename));
                    }
                }
                var sourceFilenames = exts.Select(ext => "*" + ext);

                var compilerOptions = CConfig.ToString();
                var compileCommand  = $"cl.exe /c /nologo /diagnostics:column {compilerOptions} {string.Join(" ", sourceFilenames)}";
                var msvcVersion     = version.ToString().Replace("v", "").Replace("_", ".");
                var compileBatFile  = @"call ""C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\VCVARSALL.bat"" {0} -vcvars_ver=" + msvcVersion + "\r\n" + compileCommand;
                compileBatFile = String.Format(compileBatFile, targetArch.ToString());
                File.WriteAllText("compile.bat", compileBatFile);
                var proc = Process.Start("cmd.exe", "/c " + "compile.bat");
                proc.WaitForExit();

                string[] objectFilePaths = Directory.GetFiles(".", "*.obj", SearchOption.AllDirectories);
                var      objectFiles     = objectFilePaths.ToList().Select((file) => TConstructor(File.ReadAllBytes(file))).ToList();
                return(new StaticLibrary <T>(objectFiles));
            }
        }
Exemplo n.º 5
0
        public static IntPtr GetDisasm(Machine machine)
        {
            TargetArch target = TargetArch.Target_Host;

            switch (machine)
            {
            case Machine.Amd64:
                target = TargetArch.Target_X64;
                break;

            case Machine.I386:
                target = TargetArch.Target_X86;
                break;

            case Machine.Arm64:
                target = TargetArch.Target_Arm64;
                break;

            case Machine.ArmThumb2:
                target = TargetArch.Target_Thumb;
                break;
            }
            return(InitBufferedDisasm(target));
        }
Exemplo n.º 6
0
 public static extern IntPtr InitBufferedDisasm(TargetArch Target);
Exemplo n.º 7
0
 private static extern IntPtr InitBufferedDisasm(TargetArch Target);
Exemplo n.º 8
0
        public Script(string Name, string Content, TargetPlatform platform = TargetPlatform.UNKNOWN, TargetOS os = TargetOS.UNKNOWN, TargetArch arch = TargetArch.UNKNOWN)
        {
            scriptName = Name;
            scriptBody = Content;

            this.platform = platform;
            this.os       = os;
            this.arch     = arch;
        }
Exemplo n.º 9
0
        private U Link <T, U>(IEnumerable <StaticLibrary <T> > staticLibraries, TargetArch targetArch, Func <byte[], U> UConstructor, Config.OutputType outputType)
            where T : ObjectFile, new()
            where U : IPortableExecutable, new()
        {
            switch (targetArch)
            {
            case TargetArch.x86:
                CConfig.MACHINE = Config.Machine.X86;
                break;

            case TargetArch.x64:
                CConfig.MACHINE = Config.Machine.X64;
                break;

            case TargetArch.arm:
            case TargetArch.arm64:
                CConfig.MACHINE = Config.Machine.ARM;
                break;
            }
            var outputExtension = ".exe";

            switch (outputType)
            {
            case Config.OutputType.EXE:
                CConfig.outputType = Config.OutputType.EXE;
                outputExtension    = ".exe";
                break;

            case Config.OutputType.DLL:
                CConfig.outputType = Config.OutputType.DLL;
                outputExtension    = ".dll";
                break;

            case Config.OutputType.DRIVER:
                CConfig.outputType = Config.OutputType.DRIVER;
                outputExtension    = ".sys";
                break;
            }

            using (new TemporaryContext())
            {
                foreach (var staticLibrary in staticLibraries)
                {
                    foreach (var objectFile in staticLibrary.ObjectFiles)
                    {
                        File.WriteAllBytes(Core.Utils.RandomString(10) + ".obj", objectFile.Bytes);
                    }
                }
                var outputfilename = "OUTPUT" + outputExtension;
                var linkerOptions  = CConfig.ToString();
                if (linkerOptions.Length > 0)
                {
                    linkerOptions = " " + linkerOptions;
                }
                var linkCommand = "link.exe";
                linkCommand += " /out:" + outputfilename;
                linkCommand += " /NOLOGO";
                linkCommand += linkerOptions;
                linkCommand += " *.obj";
                var msvcVersion = version.ToString().Replace("v", "").Replace("_", ".");
                var linkBatFile = @"call ""C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\VCVARSALL.bat"" {0} -vcvars_ver=" + msvcVersion + "\r\n" + linkCommand;
                linkBatFile = String.Format(linkBatFile, targetArch.ToString());
                File.WriteAllText("link.bat", linkBatFile);
                var proc = Process.Start("cmd.exe", "/c " + "link.bat");
                proc.WaitForExit();
                var pe = UConstructor(File.ReadAllBytes(outputfilename));
                if (CConfig.MAP)
                {
                    pe.Map = File.ReadAllText("OUTPUT.map");
                }
                return(pe);
            }
        }
Exemplo n.º 10
0
        internal static StaticLibrary <T> LibFileToStaticLibrary <T>(string libFile, Func <byte[], T> TConstructor, TargetArch targetArch, Version version = Version.v14_16, IEnumerable <string> includeFilter = null)
            where T : ObjectFile, new()
        {
            var objectPaths = new List <string>();

            using (new TemporaryContext())
            {
                var command     = $"lib.exe /nologo /list {libFile}";
                var msvcVersion = version.ToString().Replace("v", "").Replace("_", ".");
                var listBatFile = @"call ""C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\VCVARSALL.bat"" {0} -vcvars_ver=" + msvcVersion + "\r\n" + command;
                listBatFile = String.Format(listBatFile, targetArch.ToString());
                File.WriteAllText("list.bat", listBatFile);
                Process process = new Process();
                process.StartInfo.FileName               = "cmd.exe";
                process.StartInfo.Arguments              = "/c list.bat";
                process.StartInfo.UseShellExecute        = false;
                process.StartInfo.RedirectStandardOutput = true;
                process.StartInfo.RedirectStandardError  = true;
                process.Start();
                while (!process.StandardOutput.EndOfStream)
                {
                    string line = process.StandardOutput.ReadLine();
                    if (line.Contains("**"))
                    {
                        continue;
                    }
                    if (line.ToLower().Contains("vcvars"))
                    {
                        continue;
                    }
                    if (line != "")
                    {
                        objectPaths.Add(line);
                    }
                }
                process.WaitForExit();
            }

            objectPaths = objectPaths.Where(x => includeFilter == null || includeFilter.Any(y => x.Contains(y))).ToList();

            using (new TemporaryContext())
            {
                var msvcVersion    = version.ToString().Replace("v", "").Replace("_", ".");
                var extractBatFile = @"call ""C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\VCVARSALL.bat"" {0} -vcvars_ver=" + msvcVersion + "\r\n";
                extractBatFile = String.Format(extractBatFile, targetArch.ToString());
                File.WriteAllText("extract.bat", extractBatFile);
                foreach (var objectPath in objectPaths)
                {
                    var command = $"lib.exe /nologo {libFile} /EXTRACT:{objectPath}";
                    File.AppendAllText("extract.bat", $"\r\n{command}");
                }
                Process.Start("cmd.exe", "/c extract.bat").WaitForExit();


                // Parse the object files for their Symbol names
                string[] objectFilePaths = Directory.GetFiles(".", "*.obj", SearchOption.AllDirectories);
                var      symbolsBatFile  = @"call ""C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\VCVARSALL.bat"" {0} -vcvars_ver=" + msvcVersion + "\r\n";
                symbolsBatFile = String.Format(symbolsBatFile, targetArch.ToString());
                File.WriteAllText("symbols.bat", symbolsBatFile);
                foreach (var objectFilePath in objectFilePaths)
                {
                    var command = $"dumpbin /symbols {objectFilePath} | findstr External | findstr -v UNDEF > {objectFilePath}.txt";
                    File.AppendAllText("symbols.bat", $"\r\n{command}");
                }
                Process.Start("cmd.exe", "/c symbols.bat").WaitForExit();
                var objectFiles = new List <T>();
                foreach (var objectFilePath in objectFilePaths)
                {
                    var symbols    = new List <string>();
                    var objectFile = TConstructor(File.ReadAllBytes(objectFilePath));
                    var lines      = File.ReadLines($"{objectFilePath}.txt");
                    foreach (var line in lines)
                    {
                        var line2 = line.Trim();
                        if (line2 == "")
                        {
                            continue;
                        }
                        var symbol = line.Split("| ")[1];
                        symbols.Add(symbol);
                    }
                    objectFile.ExternalSymbols = symbols;
                    objectFiles.Add(objectFile);
                }

                return(new StaticLibrary <T>(objectFiles));
            }
        }
Exemplo n.º 11
0
        // http://www.exploit-monday.com/2013/08/writing-optimized-windows-shellcode-in-c.html
        private static byte[] CompileToShellcode(TargetArch targetArch, IShellcodeCCxxSourceIParameterlessCFunction ccxxSource, IEnumerable <ObjectFile> additionalShellcodeObjectFiles, bool optimize)
        {
            // __chkstk will be linked if large portion of the stack used. Still POC if we statically link crt


            additionalShellcodeObjectFiles = additionalShellcodeObjectFiles ?? new List <ObjectFile>();

            var source = new CCxxSource(((IShellcodeCCxxSource)ccxxSource).SourceFiles);

            var shellcodeEntryFunction = ccxxSource.Name;

            // Compile
            Compiler.Config compilerConfig;
            if (optimize)
            {
                compilerConfig = new Compiler.Config(
                    GL: true, O1: true, Os: true,                                                                              // Optimizations that differ
                    O2: false, Og: false, Ot: false, Od: false, Oy: true, Oi: true,                                            // Optimizations that are the same
                    GF: true, Gy: true, GS: false, sdl: null, Zl: false, FA: true, runtime: Compiler.Config.RunTimeLibrary.MT, // Necessary for PIE
                    callingConvention: null, EHa: null, EHs: null, EHc: null, EHr: null                                        // unsure of the effect of these, so leaving as unspecified
                    );
            }
            else
            {
                compilerConfig = new Compiler.Config(
                    GL: false, O1: false, Os: false,                                                                           // Optimizations that differ
                    O2: false, Og: false, Ot: false, Od: false, Oy: true, Oi: true,                                            // Optimizations that are the same
                    GF: true, Gy: true, GS: false, sdl: null, Zl: false, FA: true, runtime: Compiler.Config.RunTimeLibrary.MT, // Necessary for PIE
                    callingConvention: null, EHa: null, EHs: null, EHc: null, EHr: null                                        // unsure of the effect of these, so leaving as unspecified
                    );
            }

            Linker.Config linkerConfig;
            if (optimize)
            {
                linkerConfig = new Linker.Config(
                    LTCG: Linker.Config.Ltcg.ON, // Optimizations that differ
                    OPTREF: true, OPTICF: 1,     // Optimizations that are the same
                    ENTRY: "Begin", SUBSYSTEM: Linker.Config.Subsystem.CONSOLE, MAP: true, SAFESEH: false, NODEFAULTLIB: true, ORDER: new List <string>()
                {
                    "Begin", shellcodeEntryFunction
                },                                                                                                                                                                            // Necessary for PIE
                    additionalDependencies: new List <string> {
                    "libucrt.lib", "libvcruntime.lib", "libcmt.lib"
                }
                    );
            }
            else
            {
                linkerConfig = new Linker.Config(
                    LTCG: Linker.Config.Ltcg.OFF, // Optimizations that differ
                    OPTREF: true, OPTICF: 1,      // Optimizations that are the same
                    ENTRY: "Begin", SUBSYSTEM: Linker.Config.Subsystem.CONSOLE, MAP: true, SAFESEH: false, NODEFAULTLIB: true, ORDER: new List <string>()
                {
                    "Begin", shellcodeEntryFunction
                },                                                                                                                                                                            // Necessary for PIE
                    additionalDependencies: new List <string> {
                    "libucrt.lib", "libvcruntime.lib", "libcmt.lib"
                }
                    );
            }

            Executable exe;

            switch (targetArch)
            {
            case TargetArch.x64:
            {
                var additionalShellcodeObjectFiles64 = new StaticLibrary <Win64ObjectFile>(additionalShellcodeObjectFiles.Cast <Win64ObjectFile>());
                var staticLibrary = ((ICCxxCompiler <Win64ObjectFile>) new Compiler(compilerConfig)).Compile(source);
                // Since this is x64, we need to ensure that the stack is aligned before we execute our C/C++'s entry function
                var alignStackAsm = new AlignRSPMasmAssemblySource(shellcodeEntryFunction);
                var alignStackSL  = ((IAssembler <MASM, Win64ObjectFile>) new Masm()).Assemble(alignStackAsm);
                var linkerInput   = new List <StaticLibrary <Win64ObjectFile> >()
                {
                    staticLibrary, additionalShellcodeObjectFiles64, alignStackSL
                };
                exe = ((ILinker <Win64ObjectFile, Executable>) new Linker(linkerConfig)).Link(linkerInput);
                break;
            }

            case TargetArch.x86:
            {
                var additionalShellcodeObjectFiles32 = new StaticLibrary <Win32ObjectFile>(additionalShellcodeObjectFiles.Cast <Win32ObjectFile>());
                source.FindAndReplace("BeginExecutePayload", shellcodeEntryFunction);
                var staticLibrary = ((ICCxxCompiler <Win32ObjectFile>) new Compiler(compilerConfig)).Compile(source);
                var linkerInput   = new List <StaticLibrary <Win32ObjectFile> >()
                {
                    staticLibrary, additionalShellcodeObjectFiles32
                };
                exe = ((ILinker <Win32ObjectFile, Executable>) new Linker(linkerConfig)).Link(linkerInput);
                break;
            }

            default:
                throw new ArgumentException("Invalid TargetArch valid");
            }

            // Check if Position Independent Code was generate
            // Sometimes when building for 32-bit, char[] initialzied with an arrary of a certain length gets placed in the data section ...
            // Seems to be when the strlen >= 15  (>= 16 with null byte)
            // Possible solution, split up array into multiple smalle rarrarys?
            if (exe.Map.Split("Publics by Value")[1].Split("entry point")[0].Contains("0002:") || exe.Map.Split("Publics by Value")[1].Split("entry point")[0].Contains("0003:"))
            {
                Console.Error.Write(exe.Map);
                throw new Exception("Failed to generate shellcode: code dependent on data section. See Map file for more info");
            }
            // 'Begin' is the entry point to our shellcode
            if (!exe.Map.Split("Publics by Value")[1].Split("0001:")[1].Split("\n")[0].Contains("Begin"))
            {
                Console.Error.Write(exe.Map);
                throw new Exception("Failed to generate shellcode: function 'Begin' is not the first function in the CODE section. See Map file for more info");
            }

            // Extract shellcoode
            var shellcodeBytes      = PeCode.Extract(exe);
            var codeLengthHexString = exe.Map.Split("CODE")[0].Split("H ")[0].Split(" ")[^ 1];
Exemplo n.º 12
0
 public static extern long InitDisasm(TargetArch Target);
Exemplo n.º 13
0
 public Config(TargetPlatform targetPlatform = TargetPlatform.UNKNOWN, TargetOS targetOS = TargetOS.UNKNOWN, TargetArch targetArch = TargetArch.UNKNOWN)
 {
 }