内存扫描仪慢速扫描

我正在使用内存扫描仪,但扫描速度很慢..任何人都可以帮助我改进吗?

procedure FirstScan(scantype, scanvalue: string); var value :integer; dwEndAddr : dword; i:dword; mbi : TMemoryBasicInformation; begin while (VirtualQuery(Pointer(DWORD(mbi.BaseAddress) + MBI.RegionSize), MBI, SizeOf(MEMORY_BASIC_INFORMATION))=SizeOf(TMemoryBasicInformation)) do begin if (MBI.State = MEM_COMMIT) and (MBI.Protect = PAGE_READWRITE) then begin dwEndAddr := DWORD(mbi.BaseAddress) + MBI.RegionSize; for i := DWORD(MBI.BaseAddress) to (dwEndAddr - 1 - sizeof(DWORD)) do begin Application.ProcessMessages; try if scantype = '1 Byte' then begin value := PBYTE(i)^; if scanvalue = IntToStr(value) then ListBox1.Items.Add(IntToHex(i,8)); end; //others scantypes here... except Break; end; end; end; end; end; 

我已经知道我需要一次读取4096个字节的页面然后将它们存储在内存中并对其进行操作,直到我需要一个新的页面然后获得另一个4096字节的页面……

但我不知道我怎么能这样做……

有谁能够帮我? 代码可以是C或C ++ ……

要快速编写慢速代码,您可以执行一些操作。 首先,确保您的代码正确无误 。 错误的结果仍然是错误的结果,即使你很快得到它们。 为此,请确保在调用VirtualQuery ,为所有参数传递有效值。 在这个函数的开头, mbi是未初始化的,因此DWORD(mbi.BaseAddress) + MBI.RegionSize将是谁知道什么。

正确使用代码后,有两种方法可以使代码更快:

  1. 找到缓慢的部分,并使它们快速。 要做到这一点,你需要一个分析器。 分析器将在程序运行时观察您的程序,然后告诉您程序执行每个部分所花费的时间百分比。 这告诉你在哪里集中精力。

  2. 用更快的算法替换慢速算法。 这可能意味着丢掉整个函数,或者它可能意味着只修复代码的某些部分。

例如,分析可能表明您花了很多时间调用ProcessMessages 。 你不能真正使这个function更快,因为它是VCL的一部分,但你可以不那么频繁地调用它。 如果您运行此代码的线程不希望收到任何需要处理的消息,您甚至可能发现根本不需要调用它。

分析可能表明您花了很多时间进行字符串比较。 如果字符串的开头经常相等,并且通常只在结尾处有所不同,那么您可能希望更改字符串比较算法以开始比较最后一个字符而不是第一个字符串。

分析可能表明您在比较它们之前花费了大量时间将整数转换为字符串。 大多数编程语言都支持直接比较整数,因此您可以尝试使用整数比较算法,而不是使用字符串比较算法。 您可以将scanvalue转换为带有StrToInt(scanvalue)的整数,并将其直接与value进行比较。

分析可能表明您从同一输入重复计算相同的结果。 如果某个程序的某些部分的值没有变化,那么从它计算的值也不会改变。 只有在值发生变化时,才能降低转换值的成本。 例如,如果进行整数比较,那么您可能会发现scanvalue的整数版本在您的函数中没有变化。 您可以在函数开始时将scanvalue转换为一次整数,然后将value与循环内的value进行比较,而不是多次调用StrToInt(scanvalue)

我可以帮你一点……将Application.ProcessMessages从内循环中取出来。 你是为每个人打电话的。 单。 字节。 您。 扫描。 您不需要对窗口消息做出响应。 🙂

将它向上移动到外循环中,您应该看到显着的速度增加。 我会说产生一个线程并完全摆脱Application.ProcessMessages ,因为它真的不是这个代码的工作来处理,但我不确定Delphi是如何/是否执行线程。

还….你把扫描参数作为字符串传递? 如果您坚持这样做,请在开始循环之前设置int或enum或其他内容,以说明要使用的扫描类型,将值转换为有用的搜索类型,并进行比较。 字符串比较往往比整数比较慢,特别是每次创建新字符串时。

另外:您将当前指针转换您访问的每个字节的字符串。 Yech,非常慢。 相反,在程序开始时将scanvalue更改为BYTE,并直接在BYTE上进行比较。

最后 – 从for i:= DWORD(MBI.BaseAddress)循环中拉出“if scantype =’1 byte’”。 你不想为每个字节做那个“if”语句 – 而是做

 if scantype = '1 byte' then for i:= DWORD(...) else if scantype='other scan type' then... 

等等。 (是的,你应该把那个“如果scantype”比较转换为enum或诸如此类的东西。)