Exemplo n.º 1
0
        /// <summary>
        /// The legacy implementation of Rip.
        /// </summary>
        private static void LegacyRip(LegacyRipOptions options)
        {
            // Read emulated memory.
            var process = new ExternalMemory(Process.GetProcessesByName(options.ProcessName)[0]);

            process.ReadRaw((IntPtr)options.MinRamAddress, out var ps2Memory, 0x2000000);

            // Parse known file list.
            var sizeToFileMap = JsonFile.FromFileAsSizeToFileMap(options.JsonPath);

            // Read PCSX2 Logs
            using var fileStream = new FileStream(options.LogPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
            var logData = new byte[fileStream.Length];

            fileStream.Read(logData);

            var pcsx2CrashLog     = Encoding.UTF8.GetString(logData);
            var pcsx2CrashLogInfo = new ParsedCrashLog(pcsx2CrashLog.Replace("\r\n", "\n"));

            // Pattern scan for archive:
            // Build search string.
            var searchPatternBuilder = new StringBuilder($"{(options.GroupNum != -1 ? options.GroupNum.ToString("X8") : "??")} 00 00 00 "); // Note: Assuming less than 255 items!

            var groupItemCountBytes = pcsx2CrashLogInfo.Metadata.Select(x => x.NoOfItems).ToArray();
            var itemCountPattern    = Utilities.BytesToScanPattern(groupItemCountBytes);

            searchPatternBuilder.Append(itemCountPattern);

            // Scan for potential matches.
            var scanner       = new Scanner(ps2Memory);
            var patterns      = Utilities.FindAllPatterns(scanner, new CompiledScanPattern(searchPatternBuilder.ToString()));
            int archiveOffset = patterns[0].Offset;

            // Handle multiple matches.
            if (patterns.Count > 1)
            {
                // Note: Not tested.
                Console.WriteLine("More than 1 match for possible archive data. Trying to reconstruct header and searching for ID. (Note: This code is not yet implemented, exiting!)");
                return;
            }

            // Extract match from memory.
            if (sizeToFileMap.TryGetValue(pcsx2CrashLogInfo.FileSize, out var fileInfoList))
            {
                // Get user picked entry from list.
                var entry = RipUserSelectEntryFromList(fileInfoList);

                // Save file.
                var slice = ps2Memory.AsSpan().Slice(archiveOffset, entry.UncompressedSize);
                RipWriteFileToFolder(options.OutputPath, entry, slice);
            }
            else
            {
                Console.WriteLine($"No known file in JSON found. File Size from Crashlog: 0x{pcsx2CrashLogInfo.FileSize:X}");
            }
        }
        /// <summary>
        /// Creates a signature scanner given a process and a module (EXE/DLL)
        /// from which the signatures are to be found.
        /// </summary>
        /// <param name="process">The process from which</param>
        /// <param name="module">An individual module of the given process, which</param>
        public Scanner(Process process, ProcessModule module)
        {
            var externalProcess = new ExternalMemory(process);

            externalProcess.ReadRaw(module.BaseAddress, out var data, module.ModuleMemorySize);

            _data     = data;
            _gcHandle = GCHandle.Alloc(data, GCHandleType.Pinned);
            _dataPtr  = (byte *)_gcHandle.AddrOfPinnedObject();
        }
Exemplo n.º 3
0
        /// <summary>
        /// Creates a signature scanner given a process and a module (EXE/DLL)
        /// from which the signatures are to be found.
        /// </summary>
        /// <param name="process">The process from which to scan patterns in. (Not Null)</param>
        /// <param name="module">An individual module of the given process, which denotes the start and end of memory region scanned.</param>
        public Scanner(Process process, ProcessModule module)
        {
            // Optimization
            if (process.Id == _currentProcess.Id)
            {
                _dataPtr    = (byte *)module.BaseAddress;
                _dataLength = module.ModuleMemorySize;
            }
            else
            {
                var externalProcess = new ExternalMemory(process);
                externalProcess.ReadRaw(module.BaseAddress, out var data, module.ModuleMemorySize);

                _gcHandle   = GCHandle.Alloc(data, GCHandleType.Pinned);
                _dataPtr    = (byte *)_gcHandle.Value.AddrOfPinnedObject();
                _dataLength = data.Length;
            }
        }
Exemplo n.º 4
0
        /// <summary>
        /// The new implementation of Rip.
        /// </summary>
        private static void NewRip(RipOptions options)
        {
            // Read emulated memory.
            var process = new ExternalMemory(Process.GetProcessesByName(options.ProcessName)[0]);

            // Parse known file list.
            var sizeToFileMap = JsonFile.FromFileAsSizeToFileMap(options.JsonPath);

            // Read PCSX2 Logs
            using var fileStream = new FileStream(options.LogPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
            var logData = new byte[fileStream.Length];

            fileStream.Read(logData);

            // Get size, address from log.
            var pcsx2Log        = Encoding.UTF8.GetString(logData);
            var memoryDumpRegex = new Regex(@"^Addr: ([\d]*) , Size: ([\d]*), DumpFlagAddr: ([\d]*) [\n\r]+", RegexOptions.Multiline);
            var lastMatch       = memoryDumpRegex.Matches(pcsx2Log).Last();
            var archiveOffset   = Convert.ToInt32(lastMatch.Groups[1].Value);
            var fileSize        = Convert.ToInt32(lastMatch.Groups[2].Value);
            var dumpFlagAddr    = Convert.ToInt32(lastMatch.Groups[3].Value);

            // Extract match from memory.
            if (sizeToFileMap.TryGetValue(fileSize, out var fileInfoList))
            {
                var entry = RipUserSelectEntryFromList(fileInfoList);
                process.ReadRaw((IntPtr)(options.MinRamAddress + archiveOffset), out var file, entry.UncompressedSize);
                RipWriteFileToFolder(options.OutputPath, entry, file);
            }
            else
            {
                Console.WriteLine($"No known file in JSON found. Allowing game to advance.");
            }

            process.SafeWrite <int>((IntPtr)(options.MinRamAddress + dumpFlagAddr), 1);
        }