Esempio n. 1
0
        // 解析测试视频
        private List <TestVideo> ParseTestVideo(string videoPath)
        {
            if (Directory.Exists(videoPath))
            {
                List <TestVideo> testVideos = new List <TestVideo>();
                var videos = Utility.Director(videoPath).Where(f =>
                {
                    string ex = Path.GetExtension(f);
                    return(ex == ".ts" || ex == ".mp4" || ex == ".flv" || ex == ".avi");
                }).ToList();

                foreach (var item in videos)
                {
                    var _testVideoItem = new TestVideo {
                        VideoName = Path.GetFileName(item), VideoPath = Path.GetDirectoryName(item)
                    };
                    testVideos.Add(_testVideoItem);
                }

                return(testVideos);
            }
            else
            {
                MessageWindow.ShowDialog($"无法访问文件夹 [{videoPath}]", this);
            }

            return(null);
        }
Esempio n. 2
0
        public static string FindzEditPath(Compiler compiler)
        {
            var executables = compiler.MO2Ini.customExecutables;

            if (executables.size == null)
            {
                return(null);
            }

            foreach (var idx in Enumerable.Range(1, int.Parse(executables.size)))
            {
                var path = (string)executables[$"{idx}\\binary"];
                if (path == null)
                {
                    continue;
                }

                if (path.EndsWith("zEdit.exe"))
                {
                    return(Path.GetDirectoryName(path));
                }
            }

            return(null);
        }
        public static string MakePartFilename(string path, int part)
        {
            string dirName   = Path.GetDirectoryName(path);
            string baseName  = Path.GetFileNameWithoutExtension(path);
            string extension = Path.GetExtension(path);

            return($"{dirName}/{baseName}_{part}{extension}");
        }
Esempio n. 4
0
        /// <summary>
        /// Adds a file to the given mod with a given path in the mod. Fills it with random data unless
        /// random_fill == 0;
        /// </summary>
        /// <param name="mod_name"></param>
        /// <param name="path"></param>
        /// <param name="random_fill"></param>
        /// <returns></returns>
        public string AddModFile(string mod_name, string path, int random_fill = 128)
        {
            var full_path = Path.Combine(ModsFolder, mod_name, path);

            Directory.CreateDirectory(Path.GetDirectoryName(full_path));

            GenerateRandomFileData(full_path, random_fill);
            return(full_path);
        }
Esempio n. 5
0
        public string AddGameFile(string path, int i)
        {
            var full_path = Path.Combine(GameFolder, path);
            var dir       = Path.GetDirectoryName(full_path);

            if (!Directory.Exists(dir))
            {
                Directory.CreateDirectory(dir);
            }
            GenerateRandomFileData(full_path, i);
            return(full_path);
        }
Esempio n. 6
0
        public void Directory_EnumerateDirectories_OK()
        {
            var dir = Path.GetDirectoryName(typeof(AlphaFSToys).Assembly.Location);

            Console.WriteLine($"AlphaFSToys directory name {dir} or {TestContext.CurrentContext.TestDirectory}");
            Directory.SetCurrentDirectory($"{dir}\\..\\..\\..");

            var dirs = Directory.EnumerateDirectories(".").ToArray();
            var m    = dirs.Contains("bin");

            Console.WriteLine(string.Join(",", dirs));
            Assert.That(dirs.Any(x => x.EndsWith(@"\bin")));
            Assert.That(dirs.Any(x => x.EndsWith(@"\obj")));
        }
Esempio n. 7
0
        static VirtualFileSystem()
        {
            VFS         = new VirtualFileSystem();
            RootFolder  = Path.GetDirectoryName(Assembly.GetEntryAssembly().Location);
            _stagedRoot = Path.Combine(RootFolder, "vfs_staged_files");
            Utils.OnQueue(() =>
            {
                if (Directory.Exists(_stagedRoot))
                {
                    DeleteDirectory(_stagedRoot);
                }
            });

            Directory.CreateDirectory(_stagedRoot);
        }
Esempio n. 8
0
 public void BuildFolderStructure()
 {
     Info("Building Folder Structure");
     ModList.Directives
     .Select(d => Path.Combine(OutputFolder, Path.GetDirectoryName(d.To)))
     .Distinct()
     .Do(f =>
     {
         if (Directory.Exists(f))
         {
             return;
         }
         Directory.CreateDirectory(f);
     });
 }
Esempio n. 9
0
            public override async ValueTask <Directive> Run(RawSourceFile source)
            {
                if (!_mergesIndexed.TryGetValue(source.AbsolutePath, out var merge))
                {
                    return(null);
                }
                var result = source.EvolveTo <MergedPatch>();

                result.Sources = merge.plugins.Select(f =>
                {
                    var orig_path = Path.Combine(f.dataFolder, f.filename);
                    var paths     = new[]
                    {
                        orig_path,
                        orig_path + ".mohidden",
                        Path.Combine(Path.GetDirectoryName(orig_path), "optional", Path.GetFileName(orig_path))
                    };

                    var abs_path = paths.FirstOrDefault(p => File.Exists(p));

                    if (abs_path == null)
                    {
                        throw new InvalidDataException(
                            $"File {abs_path} is required to build {merge.filename} but it doesn't exist searched in: \n" + String.Join("\n", paths));
                    }

                    return(new SourcePatch
                    {
                        RelativePath = abs_path.RelativeTo(_mo2Compiler.MO2Folder),
                        Hash = _compiler.VFS.Index.ByFullPath[abs_path].Hash
                    });
                }).ToList();

                var src_data = result.Sources.Select(f => File.ReadAllBytes(Path.Combine(_mo2Compiler.MO2Folder, f.RelativePath)))
                               .ConcatArrays();

                var dst_data = File.ReadAllBytes(source.AbsolutePath);

                await using (var ms = new MemoryStream())
                {
                    await Utils.CreatePatch(src_data, dst_data, ms);

                    result.PatchID = _compiler.IncludeFile(ms.ToArray());
                }

                return(result);
            }
Esempio n. 10
0
        public void Directory_EnumerateFiles_OK()
        {
            var dir = Path.GetDirectoryName(typeof(AlphaFSToys).Assembly.Location);

            Console.WriteLine($"AlphaFSToys directory name {dir} or {TestContext.CurrentContext.TestDirectory}");
            Directory.SetCurrentDirectory(dir);

            var dirs = Directory.EnumerateFiles(".").ToArray();
            var m    = dirs.Contains("bin");

            Console.WriteLine(string.Join(",", dirs));
            //Assert.That(dirs.Contains(@".\bin"));  // NOW get full paths ? hmm.
            //Assert.That(dirs.Contains(@".\lib"));
            //Assert.That(dirs.Contains(@".\src"));
            Assert.That(dirs.Any(x => x.EndsWith(@"AlphaFSTest.pdb")));
            Assert.That(dirs.Any(x => x.EndsWith(@"AlphaFSTest.dll")));
        }
Esempio n. 11
0
 // 打开图片位置
 private void OpenImageDirClick(object sender, RoutedEventArgs e)
 {
     System.Diagnostics.Process.Start(Path.GetDirectoryName(CurrentAlarmImage().ImagePath));
 }
Esempio n. 12
0
        public static IList <string> GetGitignoreDirectories(string path, bool recursive, bool followSymlinks)
        {
            if (File.Exists(Path.Combine(path, ".gitignore")))
            {
                return new List <string> {
                           path
                }
            }
            ;

            var fileOptions = baseFileOptions;

            if (recursive)
            {
                fileOptions |= DirectoryEnumerationOptions.Recursive;
            }
            if (followSymlinks)
            {
                fileOptions &= ~DirectoryEnumerationOptions.SkipReparsePoints;
            }

            List <string> dontRecurseBelow = new List <string>
            {
                @"C:\$Recycle.Bin"
            };

            foreach (var sf in new[]
            {
                Environment.SpecialFolder.Windows,
                Environment.SpecialFolder.ProgramFiles,
                Environment.SpecialFolder.ProgramFilesX86,
            })
            {
                string p = Environment.GetFolderPath(sf);
                if (!string.IsNullOrEmpty(p))
                {
                    dontRecurseBelow.Add(p);
                }
            }

            DirectoryEnumerationFilters fileFilters = new DirectoryEnumerationFilters
            {
                ErrorFilter = (errorCode, errorMessage, pathProcessed) =>
                {
                    logger.Error($"Find file error {errorCode}: {errorMessage} on {pathProcessed}");
                    return(true);
                },
                RecursionFilter = fsei =>
                {
                    if (Utils.CancelSearch)
                    {
                        throw new OperationCanceledException();
                    }

                    if (fsei.IsDirectory && dontRecurseBelow.Any(p => fsei.FullPath.StartsWith(p, true, CultureInfo.CurrentCulture)))
                    {
                        return(false);
                    }
                    return(true);
                },
                InclusionFilter = fsei =>
                {
                    if (Utils.CancelSearch)
                    {
                        throw new OperationCanceledException();
                    }

                    if (fsei.FileName == ".gitignore")
                    {
                        dontRecurseBelow.Add(Path.GetDirectoryName(fsei.FullPath));
                        return(true);
                    }
                    return(false);
                }
            };

            try
            {
                // search down subdirectories
                var list = Directory.EnumerateFiles(path, fileOptions, fileFilters, PathFormat.FullPath)
                           .Select(s => Path.GetDirectoryName(s)).ToList();

                if (list.Count == 0)
                {
                    // not found, search up the tree
                    DirectoryInfo di = new DirectoryInfo(path);
                    while (di.Parent != null)
                    {
                        if (File.Exists(Path.Combine(di.Parent.FullName, ".gitignore")))
                        {
                            list.Add(path);
                            break;
                        }

                        di = di.Parent;
                    }
                }

                return(list);
            }
            catch (OperationCanceledException)
            {
                return(new List <string>());
            }
        }
Esempio n. 13
0
        private static void Main(string[] args)
        {
            ExceptionlessClient.Default.Startup("Kruacm8p1B6RFAw2WMnKcEqkQcnWRkF3RmPSOzlW");

            SetupNLog();
            SetupPatterns();

            _logger = LogManager.GetCurrentClassLogger();

            _fluentCommandLineParser = new FluentCommandLineParser <ApplicationArguments>
            {
                IsCaseSensitive = false
            };

            _fluentCommandLineParser.Setup(arg => arg.File)
            .As('f')
            .WithDescription("File to search. Either this or -d is required");

            _fluentCommandLineParser.Setup(arg => arg.Directory)
            .As('d')
            .WithDescription("Directory to recursively process. Either this or -f is required");

            _fluentCommandLineParser.Setup(arg => arg.SaveTo)
            .As('o')
            .WithDescription("File to save results to");

            _fluentCommandLineParser.Setup(arg => arg.GetAscii)
            .As('a')
            .SetDefault(true)
            .WithDescription("If set, look for ASCII strings. Default is true. Use -a false to disable");

            _fluentCommandLineParser.Setup(arg => arg.GetUnicode)
            .As('u')
            .SetDefault(true)
            .WithDescription("If set, look for Unicode strings. Default is true. Use -u false to disable");

            _fluentCommandLineParser.Setup(arg => arg.MinimumLength)
            .As('m').SetDefault(3).WithDescription("Minimum string length. Default is 3");

            _fluentCommandLineParser.Setup(arg => arg.BlockSizeMb)
            .As('b').SetDefault(512).WithDescription("Chunk size in MB. Valid range is 1 to 1024. Default is 512");

            _fluentCommandLineParser.Setup(arg => arg.Quiet)
            .As('q').SetDefault(false).WithDescription("Quiet mode (Do not show header or total number of hits)");

            _fluentCommandLineParser.Setup(arg => arg.QuietQuiet)
            .As('s')
            .SetDefault(false)
            .WithDescription(
                "Really Quiet mode (Do not display hits to console. Speeds up processing when using -o)");

            _fluentCommandLineParser.Setup(arg => arg.MaximumLength)
            .As('x').SetDefault(-1).WithDescription("Maximum string length. Default is unlimited\r\n");

            _fluentCommandLineParser.Setup(arg => arg.GetPatterns)
            .As('p').SetDefault(false).WithDescription("Display list of built in regular expressions");

            _fluentCommandLineParser.Setup(arg => arg.LookForString)
            .As("ls")
            .SetDefault(string.Empty)
            .WithDescription("String to look for. When set, only matching strings are returned");

            _fluentCommandLineParser.Setup(arg => arg.LookForRegex)
            .As("lr")
            .SetDefault(string.Empty)
            .WithDescription("Regex to look for. When set, only strings matching the regex are returned");

            _fluentCommandLineParser.Setup(arg => arg.StringFile)
            .As("fs")
            .SetDefault(string.Empty)
            .WithDescription("File containing strings to look for. When set, only matching strings are returned");

            _fluentCommandLineParser.Setup(arg => arg.RegexFile)
            .As("fr")
            .SetDefault(string.Empty)
            .WithDescription(
                "File containing regex patterns to look for. When set, only strings matching regex patterns are returned\r\n");


            _fluentCommandLineParser.Setup(arg => arg.AsciiRange)
            .As("ar")
            .SetDefault("[\x20-\x7E]")
            .WithDescription(
                @"Range of characters to search for in 'Code page' strings. Specify as a range of characters in hex format and enclose in quotes. Default is [\x20 -\x7E]");

            _fluentCommandLineParser.Setup(arg => arg.UnicodeRange)
            .As("ur")
            .SetDefault("[\u0020-\u007E]")
            .WithDescription(
                "Range of characters to search for in Unicode strings. Specify as a range of characters in hex format and enclose in quotes. Default is [\\u0020-\\u007E]\r\n");

            _fluentCommandLineParser.Setup(arg => arg.CodePage)
            .As("cp")
            .SetDefault(1252)
            .WithDescription(
                "Code page to use. Default is 1252. Use the Identifier value for code pages at https://goo.gl/ig6DxW");

            _fluentCommandLineParser.Setup(arg => arg.FileMask)
            .As("mask")
            .SetDefault(string.Empty)
            .WithDescription(
                "When using -d, file mask to search for. * and ? are supported. This option has no effect when using -f");

            _fluentCommandLineParser.Setup(arg => arg.RegexOnly)
            .As("ro")
            .SetDefault(false)
            .WithDescription(
                "When true, list the string matched by regex pattern vs string the pattern was found in (This may result in duplicate strings in output. ~ denotes approx. offset)");

            _fluentCommandLineParser.Setup(arg => arg.ShowOffset)
            .As("off")
            .SetDefault(false)
            .WithDescription(
                $"Show offset to hit after string, followed by the encoding (A={_fluentCommandLineParser.Object.CodePage}, U=Unicode)\r\n");

            _fluentCommandLineParser.Setup(arg => arg.SortAlpha)
            .As("sa").SetDefault(false).WithDescription("Sort results alphabetically");

            _fluentCommandLineParser.Setup(arg => arg.SortLength)
            .As("sl").SetDefault(false).WithDescription("Sort results by length");


            var header =
                $"bstrings version {Assembly.GetExecutingAssembly().GetName().Version}" +
                "\r\n\r\nAuthor: Eric Zimmerman ([email protected])" +
                "\r\nhttps://github.com/EricZimmerman/bstrings";

            var footer = @"Examples: bstrings.exe -f ""C:\Temp\UsrClass 1.dat"" --ls URL" + "\r\n\t " +
                         @" bstrings.exe -f ""C:\Temp\someFile.txt"" --lr guid" + "\r\n\t " +
                         @" bstrings.exe -f ""C:\Temp\aBigFile.bin"" --fs c:\temp\searchStrings.txt --fr c:\temp\searchRegex.txt -s" +
                         "\r\n\t " +
                         @" bstrings.exe -d ""C:\Temp"" --mask ""*.dll""" + "\r\n\t " +
                         @" bstrings.exe -d ""C:\Temp"" --ar ""[\x20-\x37]""" + "\r\n\t " +
                         @" bstrings.exe -d ""C:\Temp"" --cp 10007" + "\r\n\t " +
                         @" bstrings.exe -d ""C:\Temp"" --ls test" + "\r\n\t " +
                         @" bstrings.exe -f ""C:\Temp\someOtherFile.txt"" --lr cc -sa" + "\r\n\t " +
                         @" bstrings.exe -f ""C:\Temp\someOtherFile.txt"" --lr cc -sa -m 15 -x 22" + "\r\n\t " +
                         @" bstrings.exe -f ""C:\Temp\UsrClass 1.dat"" --ls mui -sl" + "\r\n\t ";

            _fluentCommandLineParser.SetupHelp("?", "help")
            .WithHeader(header)
            .Callback(text => _logger.Info(text + "\r\n" + footer));

            var result = _fluentCommandLineParser.Parse(args);

            if (result.HelpCalled)
            {
                return;
            }

            if (_fluentCommandLineParser.Object.GetPatterns)
            {
                _logger.Warn("Name \t\tDescription");
                foreach (var regExPattern in RegExPatterns.OrderBy(t => t.Key))
                {
                    var desc = RegExDesc[regExPattern.Key];
                    _logger.Info($"{regExPattern.Key}\t{desc}");
                }

                _logger.Info("");
                _logger.Info("To use a built in pattern, supply the Name to the --lr switch\r\n");

                return;
            }

            if (result.HasErrors)
            {
                _logger.Error("");
                _logger.Error(result.ErrorText);

                _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);

                return;
            }

            if (_fluentCommandLineParser.Object.File.IsNullOrEmpty() &&
                _fluentCommandLineParser.Object.Directory.IsNullOrEmpty())
            {
                _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);

                _logger.Warn("Either -f or -d is required. Exiting");
                return;
            }

            if (_fluentCommandLineParser.Object.File.IsNullOrEmpty() == false &&
                !File.Exists(_fluentCommandLineParser.Object.File) &&
                _fluentCommandLineParser.Object.FileMask.Length == 0)
            {
                _logger.Warn($"File '{_fluentCommandLineParser.Object.File}' not found. Exiting");
                return;
            }

            if (_fluentCommandLineParser.Object.Directory.IsNullOrEmpty() == false &&
                !Directory.Exists(_fluentCommandLineParser.Object.Directory) &&
                _fluentCommandLineParser.Object.FileMask.Length == 0)
            {
                _logger.Warn($"Directory '{_fluentCommandLineParser.Object.Directory}' not found. Exiting");
                return;
            }

            if (!_fluentCommandLineParser.Object.Quiet)
            {
                _logger.Info(header);
                _logger.Info("");
            }

            var files = new List <string>();

            if (_fluentCommandLineParser.Object.File.IsNullOrEmpty() == false)
            {
                files.Add(Path.GetFullPath(_fluentCommandLineParser.Object.File));
            }
            else
            {
                try
                {
                    if (_fluentCommandLineParser.Object.FileMask.Length > 0)
                    {
                        files.AddRange(Directory.EnumerateFiles(Path.GetFullPath(_fluentCommandLineParser.Object.Directory),
                                                                _fluentCommandLineParser.Object.FileMask, SearchOption.AllDirectories));
                    }
                    else
                    {
                        files.AddRange(Directory.EnumerateFiles(Path.GetFullPath(_fluentCommandLineParser.Object.Directory), "*",
                                                                SearchOption.AllDirectories));
                    }
                }
                catch (Exception ex)
                {
                    _logger.Error(
                        $"Error getting files in '{_fluentCommandLineParser.Object.Directory}'. Error message: {ex.Message}");
                    return;
                }
            }

            if (!_fluentCommandLineParser.Object.Quiet)
            {
                _logger.Info($"Command line: {string.Join(" ", args)}");
                _logger.Info("");
            }

            StreamWriter sw = null;

            var    globalCounter    = 0;
            var    globalHits       = 0;
            double globalTimespan   = 0;
            var    withBoundaryHits = false;

            if (_fluentCommandLineParser.Object.SaveTo.IsNullOrEmpty() == false && _fluentCommandLineParser.Object.SaveTo.Length > 0)
            {
                _fluentCommandLineParser.Object.SaveTo = _fluentCommandLineParser.Object.SaveTo.TrimEnd('\\');

                var dir = Path.GetDirectoryName(_fluentCommandLineParser.Object.SaveTo);

                if (dir != null && Directory.Exists(dir) == false)
                {
                    try
                    {
                        Directory.CreateDirectory(dir);
                    }
                    catch (Exception)
                    {
                        _logger.Warn(
                            $"Invalid path: '{_fluentCommandLineParser.Object.SaveTo}'. Results will not be saved to a file.");
                        _logger.Info("");
                        _fluentCommandLineParser.Object.SaveTo = string.Empty;
                    }
                }
                else
                {
                    if (dir == null)
                    {
                        _logger.Warn($"Invalid path: '{_fluentCommandLineParser.Object.SaveTo}");
                        _fluentCommandLineParser.Object.SaveTo = string.Empty;
                    }
                }

                if (_fluentCommandLineParser.Object.SaveTo.Length > 0 && !_fluentCommandLineParser.Object.Quiet)
                {
                    _logger.Info($"Saving hits to '{_fluentCommandLineParser.Object.SaveTo}'");
                    _logger.Info("");
                }

                if (_fluentCommandLineParser.Object.SaveTo.Length > 0)
                {
//                    try
//                    {
//                        File.Create(_fluentCommandLineParser.Object.SaveTo);
//                    }
//                    catch (Exception e)
//                    {
//                        _logger.Fatal($"Unable to create output file '{_fluentCommandLineParser.Object.SaveTo}'! Check permissions and try again! Error: {e.Message}");
//                        return;
//                    }
                    sw = new StreamWriter(_fluentCommandLineParser.Object.SaveTo, true);
                }
            }


            foreach (var file in files)
            {
                if (File.Exists(file) == false)
                {
                    _logger.Warn($"'{file}' does not exist! Skipping");
                }

                _sw = new Stopwatch();
                _sw.Start();
                var counter = 0;
                var hits    = new HashSet <string>();


                var regPattern = _fluentCommandLineParser.Object.LookForRegex;

                if (RegExPatterns.ContainsKey(_fluentCommandLineParser.Object.LookForRegex))
                {
                    regPattern = RegExPatterns[_fluentCommandLineParser.Object.LookForRegex];
                }

                if (regPattern.Length > 0 && !_fluentCommandLineParser.Object.Quiet)
                {
                    _logger.Info($"Searching via RegEx pattern: {regPattern}");
                    _logger.Info("");
                }

                var minLength = 3;
                if (_fluentCommandLineParser.Object.MinimumLength > 0)
                {
                    minLength = _fluentCommandLineParser.Object.MinimumLength;
                }

                var maxLength = -1;

                if (_fluentCommandLineParser.Object.MaximumLength > minLength)
                {
                    maxLength = _fluentCommandLineParser.Object.MaximumLength;
                }

                var chunkSizeMb = _fluentCommandLineParser.Object.BlockSizeMb < 1 ||
                                  _fluentCommandLineParser.Object.BlockSizeMb > 1024
                    ? 512
                    : _fluentCommandLineParser.Object.BlockSizeMb;
                var chunkSizeBytes = chunkSizeMb * 1024 * 1024;

                var  fileSizeBytes  = new FileInfo(file).Length;
                var  bytesRemaining = fileSizeBytes;
                long offset         = 0;

                var chunkIndex  = 1;
                var totalChunks = fileSizeBytes / chunkSizeBytes + 1;
                var hsuffix     = totalChunks == 1 ? "" : "s";

                if (!_fluentCommandLineParser.Object.Quiet)
                {
                    _logger.Info(
                        $"Searching {totalChunks:N0} chunk{hsuffix} ({chunkSizeMb} MB each) across {GetSizeReadable(fileSizeBytes)} in '{file}'");
                    _logger.Info("");
                }

                try
                {
                    MappedStream ms = null;

                    try
                    {
                        var fs =
                            File.Open(File.GetFileSystemEntryInfo(file).LongFullPath, FileMode.Open, FileAccess.Read,
                                      FileShare.Read, PathFormat.LongFullPath);

                        ms = MappedStream.FromStream(fs, Ownership.None);
                    }
                    catch (Exception)
                    {
                        _logger.Warn($"Unable to open file directly. This usually means the file is in use. Switching to raw access\r\n");
                    }

                    if (ms == null)
                    {
                        //raw mode
                        var ss = OpenFile(file);

                        ms = MappedStream.FromStream(ss, Ownership.None);
                    }


                    using (ms)
                    {
                        while (bytesRemaining > 0)
                        {
                            if (bytesRemaining <= chunkSizeBytes)
                            {
                                chunkSizeBytes = (int)bytesRemaining;
                            }
                            var chunk = new byte[chunkSizeBytes];

                            ms.Read(chunk, 0, chunkSizeBytes);

                            if (_fluentCommandLineParser.Object.GetUnicode)
                            {
                                var uh = GetUnicodeHits(chunk, minLength, maxLength, offset,
                                                        _fluentCommandLineParser.Object.ShowOffset);
                                foreach (var h in uh)
                                {
                                    hits.Add(h);
                                }
                            }

                            if (_fluentCommandLineParser.Object.GetAscii)
                            {
                                var ah = GetAsciiHits(chunk, minLength, maxLength, offset,
                                                      _fluentCommandLineParser.Object.ShowOffset);
                                foreach (var h in ah)
                                {
                                    hits.Add(h);
                                }
                            }

                            offset         += chunkSizeBytes;
                            bytesRemaining -= chunkSizeBytes;

                            if (!_fluentCommandLineParser.Object.Quiet)
                            {
                                _logger.Info(
                                    $"Chunk {chunkIndex:N0} of {totalChunks:N0} finished. Total strings so far: {hits.Count:N0} Elapsed time: {_sw.Elapsed.TotalSeconds:N3} seconds. Average strings/sec: {hits.Count/_sw.Elapsed.TotalSeconds:N0}");
                            }

                            chunkIndex += 1;
                        }

                        //do chunk boundary checks to make sure we get everything and not split things

                        if (!_fluentCommandLineParser.Object.Quiet)
                        {
                            _logger.Info(
                                "Primary search complete. Looking for strings across chunk boundaries...");
                        }

                        bytesRemaining = fileSizeBytes;
                        chunkSizeBytes = chunkSizeMb * 1024 * 1024;
                        offset         = chunkSizeBytes - _fluentCommandLineParser.Object.MinimumLength * 10 * 2;
                        //move starting point backwards for our starting point
                        chunkIndex = 0;

                        var boundaryChunkSize = _fluentCommandLineParser.Object.MinimumLength * 10 * 2 * 2;
                        //grab the same # of bytes on both sides of the boundary

                        while (bytesRemaining > 0)
                        {
                            if (offset + boundaryChunkSize > fileSizeBytes)
                            {
                                break;
                            }


                            var chunk = new byte[boundaryChunkSize];

                            ms.Read(chunk, 0, boundaryChunkSize);

                            if (_fluentCommandLineParser.Object.GetUnicode)
                            {
                                var uh = GetUnicodeHits(chunk, minLength, maxLength, offset,
                                                        _fluentCommandLineParser.Object.ShowOffset);
                                foreach (var h in uh)
                                {
                                    hits.Add("  " + h);
                                }

                                if (withBoundaryHits == false && uh.Count > 0)
                                {
                                    withBoundaryHits = uh.Count > 0;
                                }
                            }

                            if (_fluentCommandLineParser.Object.GetAscii)
                            {
                                var ah = GetAsciiHits(chunk, minLength, maxLength, offset,
                                                      _fluentCommandLineParser.Object.ShowOffset);
                                foreach (var h in ah)
                                {
                                    hits.Add("  " + h);
                                }

                                if (withBoundaryHits == false && ah.Count > 0)
                                {
                                    withBoundaryHits = true;
                                }
                            }

                            offset         += chunkSizeBytes;
                            bytesRemaining -= chunkSizeBytes;

                            chunkIndex += 1;
                        }
                    }
                }
                catch (Exception ex)
                {
                    _logger.Info("");
                    _logger.Error($"Error: {ex.Message}");
                }
                _sw.Stop();

                if (!_fluentCommandLineParser.Object.Quiet)
                {
                    _logger.Info("Search complete.");
                    _logger.Info("");
                }

                if (_fluentCommandLineParser.Object.SortAlpha)
                {
                    _logger.Info("Sorting alphabetically...");
                    _logger.Info("");
                    var tempList = hits.ToList();
                    tempList.Sort();
                    hits = new HashSet <string>(tempList);
                }
                else if (_fluentCommandLineParser.Object.SortLength)
                {
                    _logger.Info("Sorting by length...");
                    _logger.Info("");
                    var tempList = SortByLength(hits.ToList()).ToList();
                    hits = new HashSet <string>(tempList);
                }

                var fileStrings  = new HashSet <string>();
                var regexStrings = new HashSet <string>();

                //set up highlighting
                if (_fluentCommandLineParser.Object.LookForString.Length > 0)
                {
                    fileStrings.Add(_fluentCommandLineParser.Object.LookForString);
                }

                if (_fluentCommandLineParser.Object.LookForRegex.Length > 0)
                {
                    regexStrings.Add(regPattern);
                }

                if (_fluentCommandLineParser.Object.StringFile.IsNullOrEmpty() == false || _fluentCommandLineParser.Object.RegexFile.IsNullOrEmpty() == false)
                {
                    if (_fluentCommandLineParser.Object.StringFile.Length > 0)
                    {
                        if (File.Exists(_fluentCommandLineParser.Object.StringFile))
                        {
                            fileStrings.UnionWith(new HashSet <string>(File.ReadAllLines(_fluentCommandLineParser.Object.StringFile)));
                        }
                        else
                        {
                            _logger.Error($"Strings file '{_fluentCommandLineParser.Object.StringFile}' not found.");
                        }
                    }

                    if (_fluentCommandLineParser.Object.RegexFile.Length > 0)
                    {
                        if (File.Exists(_fluentCommandLineParser.Object.RegexFile))
                        {
                            regexStrings.UnionWith(new HashSet <string>(File.ReadAllLines(_fluentCommandLineParser.Object.RegexFile)));
                        }
                        else
                        {
                            _logger.Error($"Regex file '{_fluentCommandLineParser.Object.RegexFile}' not found.");
                        }
                    }
                }

                AddHighlightingRules(fileStrings.ToList());

                if (_fluentCommandLineParser.Object.RegexOnly == false)
                {
                    AddHighlightingRules(regexStrings.ToList(), true);
                }


                if (!_fluentCommandLineParser.Object.Quiet)
                {
                    _logger.Info("Processing strings...");
                    _logger.Info("");
                }

                foreach (var hit in hits)
                {
                    if (hit.Length == 0)
                    {
                        continue;
                    }

                    if (fileStrings.Count > 0 || regexStrings.Count > 0)
                    {
                        foreach (var fileString in fileStrings)
                        {
                            if (fileString.Trim().Length == 0)
                            {
                                continue;
                            }
                            if (hit.IndexOf(fileString, StringComparison.InvariantCultureIgnoreCase) < 0)
                            {
                                continue;
                            }

                            counter += 1;

                            if (_fluentCommandLineParser.Object.QuietQuiet == false)
                            {
                                _logger.Info(hit);
                            }

                            sw?.WriteLine(hit);
                        }

                        var hitoffset = "";
                        if (_fluentCommandLineParser.Object.ShowOffset)
                        {
                            hitoffset = $"~{hit.Split('\t').Last()}";
                        }

                        foreach (var regString in regexStrings)
                        {
                            if (regString.Trim().Length == 0)
                            {
                                continue;
                            }

                            try
                            {
                                var reg1 = new Regex(regString,
                                                     RegexOptions.IgnoreCase | RegexOptions.IgnorePatternWhitespace);

                                if (reg1.IsMatch(hit) == false)
                                {
                                    continue;
                                }

                                counter += 1;

                                if (_fluentCommandLineParser.Object.RegexOnly)
                                {
                                    foreach (var match in reg1.Matches(hit))
                                    {
                                        if (_fluentCommandLineParser.Object.QuietQuiet == false)
                                        {
                                            _logger.Info($"{match}\t{hitoffset}");
                                        }

                                        sw?.WriteLine($"{match}\t{hitoffset}");
                                    }
                                }
                                else
                                {
                                    if (_fluentCommandLineParser.Object.QuietQuiet == false)
                                    {
                                        _logger.Info(hit);
                                    }

                                    sw?.WriteLine(hit);
                                }
                            }
                            catch (Exception ex)
                            {
                                _logger.Error($"Error setting up regular expression '{regString}': {ex.Message}");
                            }
                        }
                    }
                    else
                    {
                        //dump all strings
                        counter += 1;

                        if (_fluentCommandLineParser.Object.QuietQuiet == false)
                        {
                            _logger.Info(hit);
                        }

                        sw?.WriteLine(hit);
                    }
                }

                if (_fluentCommandLineParser.Object.Quiet)
                {
                    continue;
                }

                var suffix = counter == 1 ? "" : "s";

                _logger.Info("");

                if (withBoundaryHits)
                {
                    _logger.Info("** Strings prefixed with 2 spaces are hits found across chunk boundaries **");
                    _logger.Info("");
                }

                _logger.Info(
                    $"Found {counter:N0} string{suffix} in {_sw.Elapsed.TotalSeconds:N3} seconds. Average strings/sec: {hits.Count/_sw.Elapsed.TotalSeconds:N0}");
                globalCounter  += counter;
                globalHits     += hits.Count;
                globalTimespan += _sw.Elapsed.TotalSeconds;
                if (files.Count > 1)
                {
                    _logger.Info(
                        "-------------------------------------------------------------------------------------\r\n");
                }
            }
            if (sw != null)
            {
                sw.Flush();
                sw.Close();
            }

            if (!_fluentCommandLineParser.Object.Quiet && files.Count > 1)
            {
                var suffix = globalCounter == 1 ? "" : "s";

                _logger.Info("");
                _logger.Info(
                    $"Found {globalCounter:N0} string{suffix} in {globalTimespan:N3} seconds. Average strings/sec: {globalHits/globalTimespan:N0}");
            }
        }
Esempio n. 14
0
        protected override async Task <ExitCode> Run()
        {
            var modListPath = (AbsolutePath)Modlist;

            if (modListPath.Extension != Consts.ModListExtension && modListPath.FileName != (RelativePath)"modlist.txt")
            {
                return(CLIUtils.Exit($"The file {Modlist} is not a valid modlist file!", ExitCode.BadArguments));
            }

            if (Copy && Move)
            {
                return(CLIUtils.Exit("You can't set both copy and move flags!", ExitCode.BadArguments));
            }

            var isModlist = modListPath.Extension == Consts.ModListExtension;

            var list = new List <TransferFile>();

            if (isModlist)
            {
                ModList modlist;

                try
                {
                    modlist = AInstaller.LoadFromFile(modListPath);
                }
                catch (Exception e)
                {
                    return(CLIUtils.Exit($"Error while loading the Modlist!\n{e}", ExitCode.Error));
                }

                if (modlist == null)
                {
                    return(CLIUtils.Exit("The Modlist could not be loaded!", ExitCode.Error));
                }

                CLIUtils.Log($"Modlist contains {modlist.Archives.Count} archives.");

                modlist.Archives.Do(a =>
                {
                    var inputPath  = Path.Combine(Input, a.Name);
                    var outputPath = Path.Combine(Output, a.Name);

                    if (!File.Exists(inputPath))
                    {
                        CLIUtils.Log($"File {inputPath} does not exist, skipping.");
                        return;
                    }

                    CLIUtils.Log($"Adding {inputPath} to the transfer list.");
                    list.Add(new TransferFile(inputPath, outputPath));

                    var metaInputPath  = Path.Combine(inputPath, ".meta");
                    var metaOutputPath = Path.Combine(outputPath, ".meta");

                    if (File.Exists(metaInputPath))
                    {
                        CLIUtils.Log($"Found meta file {metaInputPath}");
                        if (IncludeMeta)
                        {
                            CLIUtils.Log($"Adding {metaInputPath} to the transfer list.");
                            list.Add(new TransferFile(metaInputPath, metaOutputPath));
                        }
                        else
                        {
                            CLIUtils.Log($"Meta file {metaInputPath} will be ignored.");
                        }
                    }
                    else
                    {
                        CLIUtils.Log($"Found no meta file for {inputPath}");
                        if (IncludeMeta)
                        {
                            if (string.IsNullOrWhiteSpace(a.Meta))
                            {
                                CLIUtils.Log($"Meta for {a.Name} is empty, this should not be possible but whatever.");
                                return;
                            }

                            CLIUtils.Log("Adding meta from archive info the transfer list");
                            list.Add(new TransferFile(a.Meta, metaOutputPath, true));
                        }
                        else
                        {
                            CLIUtils.Log($"Meta will be ignored for {a.Name}");
                        }
                    }
                });
            }
            else
            {
                if (!Directory.Exists(Mods))
                {
                    return(CLIUtils.Exit($"Mods directory {Mods} does not exist!", ExitCode.BadArguments));
                }

                CLIUtils.Log($"Reading modlist.txt from {Modlist}");
                string[] modlist = File.ReadAllLines(Modlist);

                if (modlist == null || modlist.Length == 0)
                {
                    return(CLIUtils.Exit($"Provided modlist.txt file at {Modlist} is empty or could not be read!", ExitCode.BadArguments));
                }

                var mods = modlist.Where(s => s.StartsWith("+")).Select(s => s.Substring(1)).ToHashSet();

                if (mods.Count == 0)
                {
                    return(CLIUtils.Exit("Counted mods from modlist.txt are 0!", ExitCode.BadArguments));
                }

                CLIUtils.Log($"Found {mods.Count} mods in modlist.txt");

                var downloads = new HashSet <string>();

                Directory.EnumerateDirectories(Mods, "*", SearchOption.TopDirectoryOnly)
                .Where(d => mods.Contains(Path.GetRelativePath(Path.GetDirectoryName(d), d)))
                .Do(d =>
                {
                    var meta = Path.Combine(d, "meta.ini");
                    if (!File.Exists(meta))
                    {
                        CLIUtils.Log($"Mod meta file {meta} does not exist, skipping");
                        return;
                    }

                    string[] ini = File.ReadAllLines(meta);
                    if (ini == null || ini.Length == 0)
                    {
                        CLIUtils.Log($"Mod meta file {meta} could not be read or is empty!");
                        return;
                    }

                    ini.Where(i => !string.IsNullOrWhiteSpace(i) && i.StartsWith("installationFile="))
                    .Select(i => i.Replace("installationFile=", ""))
                    .Do(i =>
                    {
                        CLIUtils.Log($"Found installationFile {i}");
                        downloads.Add(i);
                    });
                });

                CLIUtils.Log($"Found {downloads.Count} installationFiles from mod metas.");

                Directory.EnumerateFiles(Input, "*", SearchOption.TopDirectoryOnly)
                .Where(f => downloads.Contains(Path.GetFileNameWithoutExtension(f)))
                .Do(f =>
                {
                    CLIUtils.Log($"Found archive {f}");

                    var outputPath = Path.Combine(Output, Path.GetFileName(f));

                    CLIUtils.Log($"Adding {f} to the transfer list");
                    list.Add(new TransferFile(f, outputPath));

                    var metaInputPath = Path.Combine(f, ".meta");
                    if (File.Exists(metaInputPath))
                    {
                        CLIUtils.Log($"Found meta file for {f} at {metaInputPath}");
                        if (IncludeMeta)
                        {
                            var metaOutputPath = Path.Combine(outputPath, ".meta");
                            CLIUtils.Log($"Adding {metaInputPath} to the transfer list.");
                            list.Add(new TransferFile(metaInputPath, metaOutputPath));
                        }
                        else
                        {
                            CLIUtils.Log("Meta file will be ignored");
                        }
                    }
                    else
                    {
                        CLIUtils.Log($"Found no meta file for {f}");
                    }
                });
            }

            CLIUtils.Log($"Transfer list contains {list.Count} items");
            var success = 0;
            var failed  = 0;
            var skipped = 0;

            list.Do(f =>
            {
                if (File.Exists(f.Output))
                {
                    if (Overwrite)
                    {
                        CLIUtils.Log($"Output file {f.Output} already exists, it will be overwritten");
                        if (f.IsMeta || Move)
                        {
                            CLIUtils.Log($"Deleting file at {f.Output}");
                            try
                            {
                                File.Delete(f.Output);
                            }
                            catch (Exception e)
                            {
                                CLIUtils.Log($"Could not delete file {f.Output}!\n{e}");
                                failed++;
                            }
                        }
                    }
                    else
                    {
                        CLIUtils.Log($"Output file {f.Output} already exists, skipping");
                        skipped++;
                        return;
                    }
                }

                if (f.IsMeta)
                {
                    CLIUtils.Log($"Writing meta data to {f.Output}");
                    try
                    {
                        File.WriteAllText(f.Output, f.Input, Encoding.UTF8);
                        success++;
                    }
                    catch (Exception e)
                    {
                        CLIUtils.Log($"Error while writing meta data to {f.Output}!\n{e}");
                        failed++;
                    }
                }
                else
                {
                    if (Copy)
                    {
                        CLIUtils.Log($"Copying file {f.Input} to {f.Output}");
                        try
                        {
                            File.Copy(f.Input, f.Output, Overwrite ? CopyOptions.None : CopyOptions.FailIfExists, CopyMoveProgressHandler, null);
                            success++;
                        }
                        catch (Exception e)
                        {
                            CLIUtils.Log($"Error while copying file {f.Input} to {f.Output}!\n{e}");
                            failed++;
                        }
                    }
                    else if (Move)
                    {
                        CLIUtils.Log($"Moving file {f.Input} to {f.Output}");
                        try
                        {
                            File.Move(f.Input, f.Output, Overwrite ? MoveOptions.ReplaceExisting : MoveOptions.None, CopyMoveProgressHandler, null);
                            success++;
                        }
                        catch (Exception e)
                        {
                            CLIUtils.Log($"Error while moving file {f.Input} to {f.Output}!\n{e}");
                            failed++;
                        }
                    }
                }
            });

            CLIUtils.Log($"Skipped transfers: {skipped}");
            CLIUtils.Log($"Failed transfers: {failed}");
            CLIUtils.Log($"Successful transfers: {success}");

            return(0);
        }
Esempio n. 15
0
        public static IList <string> GetGitignoreDirectories(string path, bool recursive, bool followSymlinks)
        {
            if (File.Exists(Path.Combine(path, ".gitignore")))
            {
                return new List <string> {
                           path
                }
            }
            ;

            var fileOptions = baseFileOptions;

            if (recursive)
            {
                fileOptions |= DirectoryEnumerationOptions.Recursive;
            }
            if (followSymlinks)
            {
                fileOptions &= ~DirectoryEnumerationOptions.SkipReparsePoints;
            }

            List <string> dontRecurseBelow = new List <string>();

            DirectoryEnumerationFilters fileFilters = new DirectoryEnumerationFilters
            {
                ErrorFilter = (errorCode, errorMessage, pathProcessed) =>
                {
                    logger.Error($"Find file error {errorCode}: {errorMessage} on {pathProcessed}");
                    return(true);
                },
                RecursionFilter = fsei =>
                {
                    if (fsei.IsDirectory && dontRecurseBelow.Any(p => fsei.FullPath.StartsWith(p, StringComparison.CurrentCulture)))
                    {
                        return(false);
                    }
                    return(true);
                },
                InclusionFilter = fsei =>
                {
                    if (fsei.FileName == ".gitignore")
                    {
                        dontRecurseBelow.Add(Path.GetDirectoryName(fsei.FullPath));
                        return(true);
                    }
                    return(false);
                }
            };

            var list = Directory.EnumerateFiles(path, fileOptions, fileFilters, PathFormat.FullPath)
                       .Select(s => Path.GetDirectoryName(s)).ToList();

            if (list.Count == 0)
            {
                DirectoryInfo di = new DirectoryInfo(path);
                while (di.Parent != null)
                {
                    if (File.Exists(Path.Combine(di.Parent.FullName, ".gitignore")))
                    {
                        list.Add(path);
                        break;
                    }

                    di = di.Parent;
                }
            }

            return(list);
        }
Esempio n. 16
0
        public void GetDirectoryName_Test1()
        {
            var a = Path.GetDirectoryName(@"\Data");

            Assert.That(a, Is.EqualTo(@"\"));
        }
Esempio n. 17
0
        private static void Main(string[] args)
        {
            ExceptionlessClient.Default.Startup("x3MPpeQSBUUsXl3DjekRQ9kYjyN3cr5JuwdoOBpZ");

            SetupNLog();

            _keywords = new HashSet <string> {
                "temp", "tmp"
            };

            _logger = LogManager.GetCurrentClassLogger();



            _fluentCommandLineParser = new FluentCommandLineParser <ApplicationArguments>
            {
                IsCaseSensitive = false
            };

            _fluentCommandLineParser.Setup(arg => arg.File)
            .As('f')
            .WithDescription("File to process. Either this or -d is required");

            _fluentCommandLineParser.Setup(arg => arg.Directory)
            .As('d')
            .WithDescription("Directory to recursively process. Either this or -f is required");

            _fluentCommandLineParser.Setup(arg => arg.Keywords)
            .As('k')
            .WithDescription(
                "Comma separated list of keywords to highlight in output. By default, 'temp' and 'tmp' are highlighted. Any additional keywords will be added to these.");

            _fluentCommandLineParser.Setup(arg => arg.OutFile)
            .As('o')
            .WithDescription(
                "When specified, save prefetch file bytes to the given path. Useful to look at decompressed Win10 files");

            _fluentCommandLineParser.Setup(arg => arg.Quiet)
            .As('q')
            .WithDescription(
                "Do not dump full details about each file processed. Speeds up processing when using --json or --csv. Default is FALSE\r\n")
            .SetDefault(false);

            _fluentCommandLineParser.Setup(arg => arg.JsonDirectory)
            .As("json")
            .WithDescription(
                "Directory to save json representation to. Use --pretty for a more human readable layout");

            _fluentCommandLineParser.Setup(arg => arg.CsvDirectory)
            .As("csv")
            .WithDescription(
                "Directory to save CSV results to. Be sure to include the full path in double quotes");
            _fluentCommandLineParser.Setup(arg => arg.CsvName)
            .As("csvf")
            .WithDescription("File name to save CSV formatted results to. When present, overrides default name");


            _fluentCommandLineParser.Setup(arg => arg.xHtmlDirectory)
            .As("html")
            .WithDescription(
                "Directory to save xhtml formatted results to. Be sure to include the full path in double quotes");

            _fluentCommandLineParser.Setup(arg => arg.JsonPretty)
            .As("pretty")
            .WithDescription(
                "When exporting to json, use a more human readable layout. Default is FALSE\r\n").SetDefault(false);



            _fluentCommandLineParser.Setup(arg => arg.DateTimeFormat)
            .As("dt")
            .WithDescription(
                "The custom date/time format to use when displaying timestamps. See https://goo.gl/CNVq0k for options. Default is: yyyy-MM-dd HH:mm:ss")
            .SetDefault("yyyy-MM-dd HH:mm:ss");

            _fluentCommandLineParser.Setup(arg => arg.PreciseTimestamps)
            .As("mp")
            .WithDescription(
                "When true, display higher precision for timestamps. Default is FALSE").SetDefault(false);


            var header =
                $"PECmd version {Assembly.GetExecutingAssembly().GetName().Version}" +
                "\r\n\r\nAuthor: Eric Zimmerman ([email protected])" +
                "\r\nhttps://github.com/EricZimmerman/PECmd";

            var footer = @"Examples: PECmd.exe -f ""C:\Temp\CALC.EXE-3FBEF7FD.pf""" + "\r\n\t " +
                         @" PECmd.exe -f ""C:\Temp\CALC.EXE-3FBEF7FD.pf"" --json ""D:\jsonOutput"" --jsonpretty" +
                         "\r\n\t " +
                         @" PECmd.exe -d ""C:\Temp"" -k ""system32, fonts""" + "\r\n\t " +
                         @" PECmd.exe -d ""C:\Temp"" --csv ""c:\temp"" --csvf foo.csv --json c:\temp\json" +
                         "\r\n\t " +
                         @" PECmd.exe -d ""C:\Windows\Prefetch""" + "\r\n\t " +
                         "\r\n\t" +
                         "  Short options (single letter) are prefixed with a single dash. Long commands are prefixed with two dashes\r\n";

            _fluentCommandLineParser.SetupHelp("?", "help")
            .WithHeader(header)
            .Callback(text => _logger.Info(text + "\r\n" + footer));

            var result = _fluentCommandLineParser.Parse(args);

            if (result.HelpCalled)
            {
                return;
            }

            if (result.HasErrors)
            {
                _logger.Error("");
                _logger.Error(result.ErrorText);

                _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);

                return;
            }

            if (UsefulExtension.IsNullOrEmpty(_fluentCommandLineParser.Object.File) &&
                UsefulExtension.IsNullOrEmpty(_fluentCommandLineParser.Object.Directory))
            {
                _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);

                _logger.Warn("Either -f or -d is required. Exiting");
                return;
            }

            if (UsefulExtension.IsNullOrEmpty(_fluentCommandLineParser.Object.File) == false &&
                !File.Exists(_fluentCommandLineParser.Object.File))
            {
                _logger.Warn($"File '{_fluentCommandLineParser.Object.File}' not found. Exiting");
                return;
            }

            if (UsefulExtension.IsNullOrEmpty(_fluentCommandLineParser.Object.Directory) == false &&
                !Directory.Exists(_fluentCommandLineParser.Object.Directory))
            {
                _logger.Warn($"Directory '{_fluentCommandLineParser.Object.Directory}' not found. Exiting");
                return;
            }

            if (_fluentCommandLineParser.Object.Keywords?.Length > 0)
            {
                var kws = _fluentCommandLineParser.Object.Keywords.ToLowerInvariant().Split(new[] { ',' },
                                                                                            StringSplitOptions.RemoveEmptyEntries);

                foreach (var kw in kws)
                {
                    _keywords.Add(kw.Trim());
                }
            }


            _logger.Info(header);
            _logger.Info("");
            _logger.Info($"Command line: {string.Join(" ", Environment.GetCommandLineArgs().Skip(1))}");

            if (IsAdministrator() == false)
            {
                _logger.Fatal("\r\nWarning: Administrator privileges not found!");
            }

            _logger.Info("");
            _logger.Info($"Keywords: {string.Join(", ", _keywords)}");
            _logger.Info("");

            if (_fluentCommandLineParser.Object.PreciseTimestamps)
            {
                _fluentCommandLineParser.Object.DateTimeFormat = _preciseTimeFormat;
            }

            _processedFiles = new List <IPrefetch>();

            _failedFiles = new List <string>();

            if (_fluentCommandLineParser.Object.File?.Length > 0)
            {
                IPrefetch pf = null;

                try
                {
                    pf = LoadFile(_fluentCommandLineParser.Object.File);

                    if (pf != null)
                    {
                        if (_fluentCommandLineParser.Object.OutFile.IsNullOrEmpty() == false)
                        {
                            try
                            {
                                if (Directory.Exists(Path.GetDirectoryName(_fluentCommandLineParser.Object.OutFile)) ==
                                    false)
                                {
                                    Directory.CreateDirectory(
                                        Path.GetDirectoryName(_fluentCommandLineParser.Object.OutFile));
                                }

                                PrefetchFile.SavePrefetch(_fluentCommandLineParser.Object.OutFile, pf);
                                _logger.Info($"Saved prefetch bytes to '{_fluentCommandLineParser.Object.OutFile}'");
                            }
                            catch (Exception e)
                            {
                                _logger.Error($"Unable to save prefetch file. Error: {e.Message}");
                            }
                        }


                        _processedFiles.Add(pf);
                    }
                }
                catch (UnauthorizedAccessException ex)
                {
                    _logger.Error(
                        $"Unable to access '{_fluentCommandLineParser.Object.File}'. Are you running as an administrator? Error: {ex.Message}");
                }
                catch (Exception ex)
                {
                    _logger.Error(
                        $"Error getting prefetch files in '{_fluentCommandLineParser.Object.Directory}'. Error: {ex.Message}");
                }
            }
            else
            {
                _logger.Info($"Looking for prefetch files in '{_fluentCommandLineParser.Object.Directory}'");
                _logger.Info("");

                string[] pfFiles = null;


                var f = new DirectoryEnumerationFilters();
                f.InclusionFilter = fsei =>
                {
                    if (fsei.Extension.ToUpperInvariant() == ".PF")
                    {
                        return(true);
                    }

                    return(false);
                };

                f.RecursionFilter = entryInfo => !entryInfo.IsMountPoint && !entryInfo.IsSymbolicLink;

                f.ErrorFilter = (errorCode, errorMessage, pathProcessed) => true;

                var dirEnumOptions =
                    DirectoryEnumerationOptions.Files | DirectoryEnumerationOptions.Recursive |
                    DirectoryEnumerationOptions.SkipReparsePoints | DirectoryEnumerationOptions.ContinueOnException |
                    DirectoryEnumerationOptions.BasicSearch;

                var files2 =
                    Alphaleonis.Win32.Filesystem.Directory.EnumerateFileSystemEntries(_fluentCommandLineParser.Object.Directory, dirEnumOptions, f);



                try
                {
                    pfFiles = files2.ToArray(); //Directory.GetFiles(_fluentCommandLineParser.Object.Directory, "*.pf",                        SearchOption.AllDirectories);
                }
                catch (UnauthorizedAccessException ua)
                {
                    _logger.Error(
                        $"Unable to access '{_fluentCommandLineParser.Object.Directory}'. Are you running as an administrator? Error: {ua.Message}");
                    return;
                }
                catch (Exception ex)
                {
                    _logger.Error(
                        $"Error getting prefetch files in '{_fluentCommandLineParser.Object.Directory}'. Error: {ex.Message}");
                    return;
                }

                _logger.Info($"Found {pfFiles.Length:N0} Prefetch files");
                _logger.Info("");

                var sw = new Stopwatch();
                sw.Start();

                foreach (var file in pfFiles)
                {
                    var pf = LoadFile(file);

                    if (pf != null)
                    {
                        _processedFiles.Add(pf);
                    }
                }

                sw.Stop();

                if (_fluentCommandLineParser.Object.Quiet)
                {
                    _logger.Info("");
                }

                _logger.Info(
                    $"Processed {pfFiles.Length - _failedFiles.Count:N0} out of {pfFiles.Length:N0} files in {sw.Elapsed.TotalSeconds:N4} seconds");

                if (_failedFiles.Count > 0)
                {
                    _logger.Info("");
                    _logger.Warn("Failed files");
                    foreach (var failedFile in _failedFiles)
                    {
                        _logger.Info($"  {failedFile}");
                    }
                }
            }

            if (_processedFiles.Count > 0)
            {
                _logger.Info("");

                try
                {
                    CsvWriter    csv          = null;
                    StreamWriter streamWriter = null;

                    CsvWriter    csvTl          = null;
                    StreamWriter streamWriterTl = null;


                    if (_fluentCommandLineParser.Object.CsvDirectory?.Length > 0)
                    {
                        var outName = $"{DateTimeOffset.Now:yyyyMMddHHmmss}_PECmd_Output.csv";

                        if (_fluentCommandLineParser.Object.CsvName.IsNullOrEmpty() == false)
                        {
                            outName = Path.GetFileName(_fluentCommandLineParser.Object.CsvName);
                        }

                        var outNameTl = $"{DateTimeOffset.Now:yyyyMMddHHmmss}_PECmd_Output_Timeline.csv";
                        if (_fluentCommandLineParser.Object.CsvName.IsNullOrEmpty() == false)
                        {
                            outNameTl =
                                $"{Path.GetFileNameWithoutExtension(_fluentCommandLineParser.Object.CsvName)}_Timeline{Path.GetExtension(_fluentCommandLineParser.Object.CsvName)}";
                        }


                        var outFile   = Path.Combine(_fluentCommandLineParser.Object.CsvDirectory, outName);
                        var outFileTl = Path.Combine(_fluentCommandLineParser.Object.CsvDirectory, outNameTl);


                        if (Directory.Exists(_fluentCommandLineParser.Object.CsvDirectory) == false)
                        {
                            _logger.Warn(
                                $"Path to '{_fluentCommandLineParser.Object.CsvDirectory}' does not exist. Creating...");
                            Directory.CreateDirectory(_fluentCommandLineParser.Object.CsvDirectory);
                        }

                        _logger.Warn($"CSV output will be saved to '{outFile}'");
                        _logger.Warn($"CSV time line output will be saved to '{outFileTl}'");

                        try
                        {
                            streamWriter = new StreamWriter(outFile);
                            csv          = new CsvWriter(streamWriter);


                            csv.WriteHeader(typeof(CsvOut));
                            csv.NextRecord();

                            streamWriterTl = new StreamWriter(outFileTl);
                            csvTl          = new CsvWriter(streamWriterTl);

                            csvTl.WriteHeader(typeof(CsvOutTl));
                            csvTl.NextRecord();
                        }
                        catch (Exception ex)
                        {
                            _logger.Error(
                                $"Unable to open '{outFile}' for writing. CSV export canceled. Error: {ex.Message}");
                        }
                    }

                    if (_fluentCommandLineParser.Object.JsonDirectory?.Length > 0)
                    {
                        if (Directory.Exists(_fluentCommandLineParser.Object.JsonDirectory) == false)
                        {
                            _logger.Warn(
                                $"'{_fluentCommandLineParser.Object.JsonDirectory} does not exist. Creating...'");
                            Directory.CreateDirectory(_fluentCommandLineParser.Object.JsonDirectory);
                        }

                        _logger.Warn($"Saving json output to '{_fluentCommandLineParser.Object.JsonDirectory}'");
                    }

                    XmlTextWriter xml = null;

                    if (_fluentCommandLineParser.Object.xHtmlDirectory?.Length > 0)
                    {
                        if (Directory.Exists(_fluentCommandLineParser.Object.xHtmlDirectory) == false)
                        {
                            _logger.Warn(
                                $"'{_fluentCommandLineParser.Object.xHtmlDirectory} does not exist. Creating...'");
                            Directory.CreateDirectory(_fluentCommandLineParser.Object.xHtmlDirectory);
                        }

                        var outDir = Path.Combine(_fluentCommandLineParser.Object.xHtmlDirectory,
                                                  $"{DateTimeOffset.UtcNow:yyyyMMddHHmmss}_PECmd_Output_for_{_fluentCommandLineParser.Object.xHtmlDirectory.Replace(@":\", "_").Replace(@"\", "_")}");

                        if (Directory.Exists(outDir) == false)
                        {
                            Directory.CreateDirectory(outDir);
                        }

                        var styleDir = Path.Combine(outDir, "styles");
                        if (Directory.Exists(styleDir) == false)
                        {
                            Directory.CreateDirectory(styleDir);
                        }

                        File.WriteAllText(Path.Combine(styleDir, "normalize.css"), Resources.normalize);
                        File.WriteAllText(Path.Combine(styleDir, "style.css"), Resources.style);

                        Resources.directories.Save(Path.Combine(styleDir, "directories.png"));
                        Resources.filesloaded.Save(Path.Combine(styleDir, "filesloaded.png"));

                        var outFile = Path.Combine(_fluentCommandLineParser.Object.xHtmlDirectory, outDir,
                                                   "index.xhtml");

                        _logger.Warn($"Saving HTML output to '{outFile}'");

                        xml = new XmlTextWriter(outFile, Encoding.UTF8)
                        {
                            Formatting  = Formatting.Indented,
                            Indentation = 4
                        };

                        xml.WriteStartDocument();

                        xml.WriteProcessingInstruction("xml-stylesheet", "href=\"styles/normalize.css\"");
                        xml.WriteProcessingInstruction("xml-stylesheet", "href=\"styles/style.css\"");

                        xml.WriteStartElement("document");
                    }

                    if (_fluentCommandLineParser.Object.CsvDirectory.IsNullOrEmpty() == false ||
                        _fluentCommandLineParser.Object.JsonDirectory.IsNullOrEmpty() == false ||
                        _fluentCommandLineParser.Object.xHtmlDirectory.IsNullOrEmpty() == false)
                    {
                        foreach (var processedFile in _processedFiles)
                        {
                            var o = GetCsvFormat(processedFile);

                            try
                            {
                                foreach (var dateTimeOffset in processedFile.LastRunTimes)
                                {
                                    var t = new CsvOutTl();

                                    var exePath =
                                        processedFile.Filenames.FirstOrDefault(
                                            y => y.EndsWith(processedFile.Header.ExecutableFilename));

                                    if (exePath == null)
                                    {
                                        exePath = processedFile.Header.ExecutableFilename;
                                    }

                                    t.ExecutableName = exePath;
                                    t.RunTime        = dateTimeOffset.ToString(_fluentCommandLineParser.Object.DateTimeFormat);

                                    csvTl?.WriteRecord(t);
                                    csvTl?.NextRecord();
                                }
                            }
                            catch (Exception ex)
                            {
                                _logger.Error(
                                    $"Error getting time line record for '{processedFile.SourceFilename}' to '{_fluentCommandLineParser.Object.CsvDirectory}'. Error: {ex.Message}");
                            }

                            try
                            {
                                csv?.WriteRecord(o);
                                csv?.NextRecord();
                            }
                            catch (Exception ex)
                            {
                                _logger.Error(
                                    $"Error writing CSV record for '{processedFile.SourceFilename}' to '{_fluentCommandLineParser.Object.CsvDirectory}'. Error: {ex.Message}");
                            }

                            if (_fluentCommandLineParser.Object.JsonDirectory?.Length > 0)
                            {
                                SaveJson(processedFile, _fluentCommandLineParser.Object.JsonPretty,
                                         _fluentCommandLineParser.Object.JsonDirectory);
                            }

                            //XHTML
                            xml?.WriteStartElement("Container");
                            xml?.WriteElementString("SourceFile", o.SourceFilename);
                            xml?.WriteElementString("SourceCreated", o.SourceCreated);
                            xml?.WriteElementString("SourceModified", o.SourceModified);
                            xml?.WriteElementString("SourceAccessed", o.SourceAccessed);

                            xml?.WriteElementString("LastRun", o.LastRun);

                            xml?.WriteElementString("PreviousRun0", $"{o.PreviousRun0}");
                            xml?.WriteElementString("PreviousRun1", $"{o.PreviousRun1}");
                            xml?.WriteElementString("PreviousRun2", $"{o.PreviousRun2}");
                            xml?.WriteElementString("PreviousRun3", $"{o.PreviousRun3}");
                            xml?.WriteElementString("PreviousRun4", $"{o.PreviousRun4}");
                            xml?.WriteElementString("PreviousRun5", $"{o.PreviousRun5}");
                            xml?.WriteElementString("PreviousRun6", $"{o.PreviousRun6}");

                            xml?.WriteStartElement("ExecutableName");
                            xml?.WriteAttributeString("title",
                                                      "Note: The name of the executable tracked by the pf file");
                            xml?.WriteString(o.ExecutableName);
                            xml?.WriteEndElement();

                            xml?.WriteElementString("RunCount", $"{o.RunCount}");

                            xml?.WriteStartElement("Size");
                            xml?.WriteAttributeString("title", "Note: The size of the executable in bytes");
                            xml?.WriteString(o.Size);
                            xml?.WriteEndElement();

                            xml?.WriteStartElement("Hash");
                            xml?.WriteAttributeString("title",
                                                      "Note: The calculated hash for the pf file that should match the hash in the source file name");
                            xml?.WriteString(o.Hash);
                            xml?.WriteEndElement();

                            xml?.WriteStartElement("Version");
                            xml?.WriteAttributeString("title",
                                                      "Note: The operating system that generated the prefetch file");
                            xml?.WriteString(o.Version);
                            xml?.WriteEndElement();

                            xml?.WriteElementString("Note", o.Note);

                            xml?.WriteElementString("Volume0Name", o.Volume0Name);
                            xml?.WriteElementString("Volume0Serial", o.Volume0Serial);
                            xml?.WriteElementString("Volume0Created", o.Volume0Created);

                            xml?.WriteElementString("Volume1Name", o.Volume1Name);
                            xml?.WriteElementString("Volume1Serial", o.Volume1Serial);
                            xml?.WriteElementString("Volume1Created", o.Volume1Created);


                            xml?.WriteStartElement("Directories");
                            xml?.WriteAttributeString("title",
                                                      "A comma separated list of all directories accessed by the executable");
                            xml?.WriteString(o.Directories);
                            xml?.WriteEndElement();

                            xml?.WriteStartElement("FilesLoaded");
                            xml?.WriteAttributeString("title",
                                                      "A comma separated list of all files that were loaded by the executable");
                            xml?.WriteString(o.FilesLoaded);
                            xml?.WriteEndElement();

                            xml?.WriteEndElement();
                        }


                        //Close CSV stuff
                        streamWriter?.Flush();
                        streamWriter?.Close();

                        streamWriterTl?.Flush();
                        streamWriterTl?.Close();

                        //Close XML
                        xml?.WriteEndElement();
                        xml?.WriteEndDocument();
                        xml?.Flush();
                    }
                }
                catch (Exception ex)
                {
                    _logger.Error($"Error exporting data! Error: {ex.Message}");
                }
            }
        }
Esempio n. 18
0
        public void AlphaFS_Path_GetLongPath()
        {
            Console.WriteLine("Path.GetLongPath()");

            var pathCnt  = 0;
            var errorCnt = 0;

            UnitTestConstants.StopWatcher(true);
            foreach (var path in UnitTestConstants.InputPaths)
            {
                string actual = null;

                Console.WriteLine("\n#{0:000}\tInput Path: [{1}]", ++pathCnt, path);

                // AlphaFS
                try
                {
                    actual = Path.GetLongPath(path);

                    if (Path.IsUncPath(path))
                    {
                        Assert.IsTrue(actual.StartsWith(Path.LongPathUncPrefix), "Path should start with a long unc path prefix.");
                    }
                    else
                    {
                        var c = path[0];
                        if (!Path.IsPathRooted(path) && ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z')))
                        {
                            Assert.IsFalse(actual.StartsWith(Path.LongPathPrefix), "Path should not start with a long path prefix.");
                        }
                        else
                        {
                            if (!Path.IsPathRooted(path) && !Utils.IsNullOrWhiteSpace(Path.GetDirectoryName(path)))
                            {
                                Assert.IsTrue(actual.StartsWith(Path.LongPathUncPrefix), "Path should start with a long path prefix.");
                            }
                        }
                    }
                }
                catch (Exception ex)
                {
                    Console.WriteLine("\tCaught [AlphaFS] {0}: [{1}]", ex.GetType().FullName, ex.Message.Replace(Environment.NewLine, "  "));

                    errorCnt++;
                }
                Console.WriteLine("\t   AlphaFS   : [{0}]", actual ?? "null");
            }
            Console.WriteLine("\n{0}", UnitTestConstants.Reporter(true));

            Assert.AreEqual(0, errorCnt, "No errors were expected.");
        }
Esempio n. 19
0
    public AppCompatCache(string filename, int controlSet, bool noLogs)
    {
        byte[] rawBytes = null;
        Caches = new List <IAppCompatCache>();

        var controlSetIds = new List <int>();

        RegistryKey subKey = null;

        var isLiveRegistry = string.IsNullOrEmpty(filename);

        if (isLiveRegistry)
        {
            if (!RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
            {
                throw new NotSupportedException("Live Registry support is not supported on non-Windows platforms.");
            }

            var keyCurrUser = Microsoft.Win32.Registry.LocalMachine;
            var subKey2     =
                keyCurrUser.OpenSubKey(@"SYSTEM\CurrentControlSet\Control\Session Manager\AppCompatCache");

            if (subKey2 == null)
            {
                subKey2 =
                    keyCurrUser.OpenSubKey(@"SYSTEM\CurrentControlSet\Control\Session Manager\AppCompatibility");

                if (subKey2 == null)
                {
                    Console.WriteLine(
                        @"'CurrentControlSet\Control\Session Manager\AppCompatCache' key not found! Exiting");
                    return;
                }
            }

            rawBytes = (byte[])subKey2.GetValue("AppCompatCache", null);

            subKey2    = keyCurrUser.OpenSubKey(@"SYSTEM\Select");
            ControlSet = (int)subKey2.GetValue("Current");

            var is32Bit = Is32Bit(filename, null);

            var cache = Init(rawBytes, is32Bit, ControlSet);

            Caches.Add(cache);

            return;
        }

        RegistryHive reg;

        if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
        {
            Privilege[] privileges = { Privilege.EnableDelegation, Privilege.Impersonate, Privilege.Tcb };
            using var enabler = new PrivilegeEnabler(Privilege.Backup, privileges);
        }

        ControlSet = controlSet;

        if (File.Exists(filename) == false && Helper.RawFileExists(filename) == false)
        {
            throw new FileNotFoundException($"File not found ({filename})!");
        }

        var dirname  = Path.GetDirectoryName(Path.GetFullPath(filename));
        var hiveBase = Path.GetFileName(filename);



        List <RawCopyReturn> rawFiles = null;

        try
        {
            reg = new RegistryHive(filename)
            {
                RecoverDeleted = true
            };
        }
        catch (IOException)
        {
            //file is in use

            if (Helper.IsAdministrator() == false)
            {
                throw new UnauthorizedAccessException("Administrator privileges not found!");
            }

            Log.Warning("'{Filename}' is in use. Rerouting...", filename);

            var files = new List <string>();
            files.Add(filename);

            var logFiles = Directory.GetFiles(dirname, $"{hiveBase}.LOG?").ToList();

            var log1 = $"{dirname}\\{hiveBase}.LOG1";
            var log2 = $"{dirname}\\{hiveBase}.LOG2";

            if (logFiles.Count == 0)
            {
                if (Helper.RawFileExists(log1))
                {
                    logFiles.Add(log1);
                }

                if (Helper.RawFileExists(log2))
                {
                    logFiles.Add(log2);
                }
            }

            foreach (var logFile in logFiles)
            {
                files.Add(logFile);
            }

            rawFiles = Helper.GetRawFiles(files);
            var b = new byte[rawFiles.First().FileStream.Length];

            rawFiles.First().FileStream.Read(b, 0, (int)rawFiles.First().FileStream.Length);


            reg = new RegistryHive(b, rawFiles.First().InputFilename);
        }

        if (reg.Header.PrimarySequenceNumber != reg.Header.SecondarySequenceNumber)
        {
            if (string.IsNullOrEmpty(dirname))
            {
                dirname = ".";
            }

            var logFiles = Directory.GetFiles(dirname, $"{hiveBase}.LOG?").ToList();

            var log1 = $"{dirname}\\{hiveBase}.LOG1";
            var log2 = $"{dirname}\\{hiveBase}.LOG2";

            if (logFiles.Count == 0)
            {
                if (File.Exists(log1))
                {
                    logFiles.Add(log1);
                }

                if (File.Exists(log2))
                {
                    logFiles.Add(log2);
                }
            }

            if (logFiles.Count == 0)
            {
                if (Helper.IsAdministrator())
                {
                    if (Helper.RawFileExists(log1))
                    {
                        logFiles.Add(log1);
                    }

                    if (Helper.RawFileExists(log2))
                    {
                        logFiles.Add(log2);
                    }
                }
                else
                {
                    Log.Fatal("Log files not found and no administrator access to look for them!");
                }
            }


            if (logFiles.Count == 0)
            {
                if (noLogs == false)
                {
                    Log.Warning(
                        "Registry hive is dirty and no transaction logs were found in the same directory! LOGs should have same base name as the hive. Aborting!!");
                    throw new Exception(
                              "Sequence numbers do not match and transaction logs were not found in the same directory as the hive. Aborting");
                }

                Log.Warning(
                    "Registry hive is dirty and no transaction logs were found in the same directory. Data may be missing! Continuing anyways...");
            }
            else
            {
                if (noLogs == false)
                {
                    if (rawFiles != null)
                    {
                        var lt = new List <TransactionLogFileInfo>();
                        foreach (var rawCopyReturn in rawFiles.Skip(1).ToList())
                        {
                            var b = new byte[rawCopyReturn.FileStream.Length];

                            var tt = new TransactionLogFileInfo(rawCopyReturn.InputFilename,
                                                                b);
                            lt.Add(tt);
                        }

                        reg.ProcessTransactionLogs(lt, true);
                    }
                    else
                    {
                        reg.ProcessTransactionLogs(logFiles.ToList(), true);
                    }
                }
                else
                {
                    Log.Warning(
                        "Registry hive is dirty and transaction logs were found in the same directory, but --nl was provided. Data may be missing! Continuing anyways...");
                }
            }
        }


        reg.ParseHive();

        if (controlSet == -1)
        {
            for (var i = 0; i < 10; i++)
            {
                subKey = reg.GetKey($@"ControlSet00{i}\Control\Session Manager\AppCompatCache");

                if (subKey == null)
                {
                    subKey = reg.GetKey($@"ControlSet00{i}\Control\Session Manager\AppCompatibility");
                }

                if (subKey != null)
                {
                    controlSetIds.Add(i);
                }
            }

            if (controlSetIds.Count > 1)
            {
                Log.Warning(
                    "***The following ControlSet00x keys will be exported: {Cs}. Use -c to process keys individually", string.Join(",", controlSetIds));
            }
        }
        else
        {
            //a control set was passed in
            subKey = reg.GetKey($@"ControlSet00{ControlSet}\Control\Session Manager\AppCompatCache");

            if (subKey == null)
            {
                subKey = reg.GetKey($@"ControlSet00{ControlSet}\Control\Session Manager\AppCompatibility");
            }

            if (subKey == null)
            {
                throw new Exception($"Could not find ControlSet00{ControlSet}. Exiting");
            }

            controlSetIds.Add(ControlSet);
        }


        var is32 = Is32Bit(filename, reg);


        Log.Debug("**** Found {Count} ids to process", controlSetIds.Count);


        foreach (var id in controlSetIds)
        {
            Log.Debug("**** Processing id {Id}", id);

            //  var hive2 = new RegistryHiveOnDemand(filename);

            subKey = reg.GetKey($@"ControlSet00{id}\Control\Session Manager\AppCompatCache");

            if (subKey == null)
            {
                Log.Debug("**** Initial subkey null, getting appCompatability key");
                subKey = reg.GetKey($@"ControlSet00{id}\Control\Session Manager\AppCompatibility");
            }

            Log.Debug("**** Looking for AppCompatcache value");

            var val = subKey?.Values.SingleOrDefault(c => c.ValueName == "AppCompatCache");

            if (val != null)
            {
                Log.Debug("**** Found AppCompatcache value");
                rawBytes = val.ValueDataRaw;
            }

            if (rawBytes == null)
            {
                Log.Error("'AppCompatCache' value not found for 'ControlSet00{Id}'! Exiting", id);
            }

            var cache = Init(rawBytes, is32, id);

            Caches.Add(cache);
        }
    }
Esempio n. 20
0
 public static bool IsMO2Running(string mo2Path)
 {
     Process[] processList = Process.GetProcesses();
     return(processList.Where(process => process.ProcessName == "ModOrganizer").Any(process => Path.GetDirectoryName(process.MainModule?.FileName) == mo2Path));
 }
Esempio n. 21
0
        static void Main(string[] args)
        {
            Exceptionless.ExceptionlessClient.Default.Startup("fTcEOUkt1CxljTyOZfsr8AcSGQwWE4aYaYqk7cE1");
            SetupNLog();

            _logger = LogManager.GetCurrentClassLogger();

            _fluentCommandLineParser = new FluentCommandLineParser <ApplicationArguments>
            {
                IsCaseSensitive = false
            };

            _fluentCommandLineParser.Setup(arg => arg.Directory)
            .As('d')
            .WithDescription(
                "Directory to look for hives (recursively). -f or -d is required.");
            _fluentCommandLineParser.Setup(arg => arg.HiveFile)
            .As('f')
            .WithDescription("Hive to process. -f or -d is required.\r\n");

            _fluentCommandLineParser.Setup(arg => arg.OutDirectory)
            .As("out")
            .WithDescription(
                "Directory to save updated hives to. Only dirty hives with logs applied will end up in --out directory\r\n");

            _fluentCommandLineParser.Setup(arg => arg.CopyAlways)
            .As("ca")
            .WithDescription(
                "When true, always copy hives to --out directory, even if they aren't dirty. Default is TRUE").SetDefault(true);

            _fluentCommandLineParser.Setup(arg => arg.CompressNames)
            .As("cn")
            .WithDescription(
                "When true, compress names for profile based hives. Default is TRUE\r\n").SetDefault(true);

            _fluentCommandLineParser.Setup(arg => arg.Debug)
            .As("debug")
            .WithDescription("Show debug information during processing").SetDefault(false);

            _fluentCommandLineParser.Setup(arg => arg.Trace)
            .As("trace")
            .WithDescription("Show trace information during processing").SetDefault(false);

            var header =
                $"rla version {Assembly.GetExecutingAssembly().GetName().Version}" +
                "\r\n\r\nAuthor: Eric Zimmerman ([email protected])" +
                "\r\nhttps://github.com/EricZimmerman/RECmd\r\n\r\nNote: Enclose all strings containing spaces (and all RegEx) with double quotes";

            var footer = @"Example: rla.exe --f ""C:\Temp\UsrClass 1.dat"" --out C:\temp" +
                         "\r\n\t " +
                         @"rla.exe --d ""D:\temp\"" --out c:\temp" + "\r\n";

            _fluentCommandLineParser.SetupHelp("?", "help").WithHeader(header)
            .Callback(text => _logger.Info(text + "\r\n" + footer));

            var result = _fluentCommandLineParser.Parse(args);

            if (_fluentCommandLineParser.Object.HiveFile.IsNullOrEmpty() == false ||
                _fluentCommandLineParser.Object.Directory.IsNullOrEmpty() == false)
            {
                if (_fluentCommandLineParser.Object.OutDirectory.IsNullOrEmpty())
                {
                    _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);
                    Console.WriteLine();
                    _logger.Warn($"--out is required. Exiting");
                    Console.WriteLine();
                    return;
                }
            }

            if (_fluentCommandLineParser.Object.Debug)
            {
                foreach (var r in LogManager.Configuration.LoggingRules)
                {
                    r.EnableLoggingForLevel(LogLevel.Debug);
                }

                LogManager.ReconfigExistingLoggers();
                _logger.Debug("Enabled debug messages...");
            }

            if (_fluentCommandLineParser.Object.Trace)
            {
                foreach (var r in LogManager.Configuration.LoggingRules)
                {
                    r.EnableLoggingForLevel(LogLevel.Trace);
                }

                LogManager.ReconfigExistingLoggers();
                _logger.Trace("Enabled trace messages...");
            }

            if (result.HelpCalled)
            {
                return;
            }

            if (result.HasErrors)
            {
                _logger.Error("");
                _logger.Error(result.ErrorText);

                _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);

                return;
            }

            var hivesToProcess = new List <string>();

            _logger.Info(header);
            _logger.Info("");
            _logger.Info($"Command line: {string.Join(" ", Environment.GetCommandLineArgs().Skip(1))}\r\n");

            if (_fluentCommandLineParser.Object.HiveFile?.Length > 0)
            {
                if (File.Exists(_fluentCommandLineParser.Object.HiveFile) == false)
                {
                    _logger.Error($"File '{_fluentCommandLineParser.Object.HiveFile}' does not exist.");
                    return;
                }

                hivesToProcess.Add(_fluentCommandLineParser.Object.HiveFile);
            }
            else if (_fluentCommandLineParser.Object.Directory?.Length > 0)
            {
                if (Directory.Exists(_fluentCommandLineParser.Object.Directory) == false)
                {
                    _logger.Error($"Directory '{_fluentCommandLineParser.Object.Directory}' does not exist.");
                    return;
                }

                var okFileParts = new HashSet <string>();
                okFileParts.Add("USRCLASS");
                okFileParts.Add("NTUSER");
                okFileParts.Add("SYSTEM");
                okFileParts.Add("SAM");
                okFileParts.Add("SOFTWARE");
                okFileParts.Add("AMCACHE");
                okFileParts.Add("SYSCACHE");
                okFileParts.Add("SECURITY");
                okFileParts.Add("DRIVERS");
                okFileParts.Add("COMPONENTS");

                var f = new DirectoryEnumerationFilters();
                f.InclusionFilter = fsei =>
                {
                    if (fsei.Extension.ToUpperInvariant() == ".LOG1" || fsei.Extension.ToUpperInvariant() == ".LOG2" ||
                        fsei.Extension.ToUpperInvariant() == ".DLL" ||
                        fsei.Extension.ToUpperInvariant() == ".LOG" ||
                        fsei.Extension.ToUpperInvariant() == ".CSV" ||
                        fsei.Extension.ToUpperInvariant() == ".BLF" ||
                        fsei.Extension.ToUpperInvariant() == ".REGTRANS-MS" ||
                        fsei.Extension.ToUpperInvariant() == ".EXE" ||
                        fsei.Extension.ToUpperInvariant() == ".TXT" || fsei.Extension.ToUpperInvariant() == ".INI")
                    {
                        return(false);
                    }

                    var foundOkFilePart = false;

                    foreach (var okFilePart in okFileParts)
                    {
                        if (fsei.FileName.ToUpperInvariant().Contains(okFilePart))
                        {
                            foundOkFilePart = true;
                            //     return true;
                        }
                    }

                    if (foundOkFilePart == false)
                    {
                        return(false);
                    }

                    var fi = new FileInfo(fsei.FullPath);

                    if (fi.Length < 4)
                    {
                        return(false);
                    }

                    try
                    {
                        using (var fs = new FileStream(fsei.FullPath, FileMode.Open, FileAccess.Read))
                        {
                            using (var br = new BinaryReader(fs, new ASCIIEncoding()))
                            {
                                try
                                {
                                    var chunk = br.ReadBytes(4);

                                    var sig = BitConverter.ToInt32(chunk, 0);

                                    if (sig == 0x66676572)
                                    {
                                        return(true);
                                    }
                                }
                                catch (Exception)
                                {
                                }

                                return(false);
                            }
                        }
                    }
                    catch (IOException)
                    {
                        if (Helper.IsAdministrator() == false)
                        {
                            throw new UnauthorizedAccessException("Administrator privileges not found!");
                        }

                        var files = new List <string>();
                        files.Add(fsei.FullPath);

                        var rawf = Helper.GetFiles(files);

                        if (rawf.First().FileStream.Length == 0)
                        {
                            return(false);
                        }

                        try
                        {
                            var b = new byte[4];
                            rawf.First().FileStream.ReadExactly(b, 4);

                            var sig = BitConverter.ToInt32(b, 0);

                            if (sig == 0x66676572)
                            {
                                return(true);
                            }
                        }
                        catch (Exception)
                        {
                        }

                        return(false);
                    }
                };

                f.RecursionFilter = entryInfo => !entryInfo.IsMountPoint && !entryInfo.IsSymbolicLink;

                f.ErrorFilter = (errorCode, errorMessage, pathProcessed) => true;

                var dirEnumOptions =
                    DirectoryEnumerationOptions.Files | DirectoryEnumerationOptions.Recursive |
                    DirectoryEnumerationOptions.SkipReparsePoints | DirectoryEnumerationOptions.ContinueOnException |
                    DirectoryEnumerationOptions.BasicSearch;

                if (Directory.Exists(_fluentCommandLineParser.Object.OutDirectory) == false)
                {
                    _logger.Info($"Creating --out directory '{_fluentCommandLineParser.Object.OutDirectory}'...");
                    Directory.CreateDirectory(_fluentCommandLineParser.Object.OutDirectory);
                }
                else
                {
                    if (Directory.GetFiles(_fluentCommandLineParser.Object.OutDirectory).Length > 0 && _fluentCommandLineParser.Object.CompressNames)
                    {
                        _logger.Warn($"'{_fluentCommandLineParser.Object.OutDirectory}' contains files! This may cause --cn to revert back to uncompressed names. Ideally, '{_fluentCommandLineParser.Object.OutDirectory}' should be empty.");
                        Console.WriteLine();
                    }
                }

                _logger.Fatal($"Searching '{_fluentCommandLineParser.Object.Directory}' for hives...");

                var files2 =
                    Directory.EnumerateFileSystemEntries(_fluentCommandLineParser.Object.Directory, dirEnumOptions, f);

                var count = 0;

                try
                {
                    hivesToProcess.AddRange(files2);
                    count = hivesToProcess.Count;

                    _logger.Info($"\tHives found: {count:N0}");
                }
                catch (Exception ex)
                {
                    _logger.Fatal($"Could not access all files in '{_fluentCommandLineParser.Object.Directory}'! Error: {ex.Message}");
                    _logger.Error("");
                    _logger.Fatal("Rerun the program with Administrator privileges to try again\r\n");
                    //Environment.Exit(-1);
                }
            }
            else
            {
                _fluentCommandLineParser.HelpOption.ShowHelp(_fluentCommandLineParser.Options);
                return;
            }


            if (hivesToProcess.Count == 0)
            {
                _logger.Warn("No hives were found. Exiting...");

                return;
            }

            _sw = new Stopwatch();
            _sw.Start();

            foreach (var hiveToProcess in hivesToProcess)
            {
                _logger.Info("");

                byte[] updatedBytes = null;

                _logger.Info($"Processing hive '{hiveToProcess}'");

                if (File.Exists(hiveToProcess) == false)
                {
                    _logger.Warn($"'{hiveToProcess}' does not exist. Skipping");
                    continue;
                }

                try
                {
                    RegistryHive reg;

                    var dirname  = Path.GetDirectoryName(hiveToProcess);
                    var hiveBase = Path.GetFileName(hiveToProcess);

                    List <RawCopyReturn> rawFiles = null;

                    try
                    {
                        using (var fs = new FileStream(hiveToProcess, FileMode.Open, FileAccess.Read))
                        {
                            reg = new RegistryHive(fs.ReadFully(), hiveToProcess)
                            {
                            };
                        }
                    }
                    catch (IOException)
                    {
                        //file is in use

                        if (Helper.IsAdministrator() == false)
                        {
                            throw new UnauthorizedAccessException("Administrator privileges not found!");
                        }

                        _logger.Warn($"\t'{hiveToProcess}' is in use. Rerouting...\r\n");

                        var files = new List <string>();
                        files.Add(hiveToProcess);

                        var logFiles = Directory.GetFiles(dirname, $"{hiveBase}.LOG?");

                        foreach (var logFile in logFiles)
                        {
                            files.Add(logFile);
                        }

                        rawFiles = Helper.GetFiles(files);

                        if (rawFiles.First().FileStream.Length == 0)
                        {
                            continue;
                        }

                        var bb = rawFiles.First().FileStream.ReadFully();

                        reg = new RegistryHive(bb, rawFiles.First().InputFilename);
                    }

                    if (reg.Header.PrimarySequenceNumber != reg.Header.SecondarySequenceNumber)
                    {
                        if (string.IsNullOrEmpty(dirname))
                        {
                            dirname = ".";
                        }

                        var logFiles = Directory.GetFiles(dirname, $"{hiveBase}.LOG?");

                        if (logFiles.Length == 0)
                        {
                            if (_fluentCommandLineParser.Object.CopyAlways)
                            {
                                _logger.Info($"\tHive '{hiveToProcess}' is dirty, but no logs were found in the same directory. --ca is true. Copying...");
                                updatedBytes = File.ReadAllBytes(hiveToProcess);
                            }
                            else
                            {
                                _logger.Info($"\tHive '{hiveToProcess}' is dirty and no transaction logs were found in the same directory. --ca is false. Skipping...");
                                continue;
                            }
                        }

                        if (updatedBytes == null)
                        {
                            if (rawFiles != null)
                            {
                                var lt = new List <TransactionLogFileInfo>();
                                foreach (var rawCopyReturn in rawFiles.Skip(1).ToList())
                                {
                                    var bb1 = rawCopyReturn.FileStream.ReadFully();

                                    var tt = new TransactionLogFileInfo(rawCopyReturn.InputFilename, bb1);
                                    lt.Add(tt);
                                }

                                updatedBytes = reg.ProcessTransactionLogs(lt);
                            }
                            else
                            {
                                updatedBytes = reg.ProcessTransactionLogs(logFiles.ToList());
                            }
                        }
                    }

                    if (updatedBytes == null)
                    {
                        if (_fluentCommandLineParser.Object.CopyAlways)
                        {
                            _logger.Info($"\tHive '{hiveToProcess}' is not dirty, but --ca is true. Copying...");
                            updatedBytes = File.ReadAllBytes(hiveToProcess);
                        }
                        else
                        {
                            _logger.Info($"\tHive '{hiveToProcess}' is not dirty and --ca is false. Skipping...");
                            continue;
                        }
                    }

                    var outFile    = hiveToProcess.Replace(":", "").Replace("\\", "_");
                    var outFileAll = Path.Combine(_fluentCommandLineParser.Object.OutDirectory, outFile);

                    if (_fluentCommandLineParser.Object.CompressNames &&
                        (outFileAll.ToUpperInvariant().Contains("NTUSER") || outFileAll.ToUpperInvariant().Contains("USRCLASS")))
                    {
                        var dl   = hiveToProcess[0].ToString();
                        var segs = hiveToProcess.SplitAndTrim('\\');

                        var profile  = segs[2];
                        var filename = Path.GetFileName(hiveToProcess);

                        var outFile2 = $"{dl}_{profile}_{filename}";

                        outFileAll = Path.Combine(_fluentCommandLineParser.Object.OutDirectory, outFile2);
                    }

                    if (File.Exists(outFileAll))
                    {
                        var oldOut = outFileAll;

                        outFileAll = Path.Combine(_fluentCommandLineParser.Object.OutDirectory, outFile);

                        _logger.Warn($"\tFile '{oldOut}' exists! Saving as non-compressed name: '{outFileAll}'");
                    }

                    _logger.Fatal($"\tSaving updated hive to '{outFileAll}'");

                    using (var fs = new FileStream(outFileAll, FileMode.Create))
                    {
                        fs.Write(updatedBytes, 0, updatedBytes.Length);

                        fs.Flush();

                        fs.Close();
                    }
                }
                catch (Exception ex)
                {
                    if (ex.Message.Contains("Sequence numbers do not match and transaction") == false)
                    {
                        if (ex.Message.Contains("Administrator privileges not found"))
                        {
                            _logger.Fatal($"Could not access '{hiveToProcess}' because it is in use");
                            _logger.Error("");
                            _logger.Fatal("Rerun the program with Administrator privileges to try again\r\n");
                        }
                        else
                        {
                            _logger.Error($"There was an error: {ex.Message}");
                        }
                    }
                }
            }

            _sw.Stop();
            _logger.Info("");

            _logger.Info($"Total processing time: {_sw.Elapsed.TotalSeconds:N3} seconds");
            _logger.Info("");
        }