关于c builder:如何在Delphi 2006或更早版本的可执行文件上启用DEP / NX和ASLR?

How can I enable DEP/NX and ASLR on a Delphi 2006 or earlier executable?

Delphi 2007(及更高版本)支持通过以下三种技术之一启用DEP和ASLR:

  • 使用dcc32进行编译时添加命令行开关–dynamicbase
  • 将预处理器命令{$DYNAMICBASE ON}添加到源代码中
  • 手动或在标头中的位中进行或,或在源代码中与{$SETPEOPTFLAGS $40}

我希望能够使用Delphi 2006和C Builder 2006(又名BDS 2006)执行相同的操作。有人知道该怎么做吗?


设置PE标志

您可以使用{$SetPEOptFlags $40}设置DEP标志,并使用{$SetPEOptFlags $100}设置ASLR标志。要设置两者,请使用{$SetPEOptFlags $140}

如果Windows.pas单元中具有必需定义的Delphi版本,则可以使用更具可读性的内容:

1
2
{$SetPEOptFlags IMAGE_DLLCHARACTERISTICS_NX_COMPAT or
    IMAGE_DLLCHARACTERISTICS_DYNAMIC_BASE }

通常,您在.dpr文件中包括$SetPEOptFlags设置。因此,您需要确保.dpr文件中使用Windows子句,以使这些IMAGE_XXX常量可用。

在运行时设置DEP策略

对于不支持基于PE标志的方法的版本,您可以在应用程序初始化的早期调用此函数:

1
2
3
4
5
6
7
8
9
10
11
12
13
procedure EnableDEP;
const
  PROCESS_DEP_ENABLE: DWORD=$00000001;
var
  SetProcessDEPPolicy: function(dwFlags: DWORD): BOOL; stdcall;
begin
  SetProcessDEPPolicy := GetProcAddress(GetModuleHandle(kernel32),
     'SetProcessDEPPolicy');
  if Assigned(SetProcessDEPPolicy) then begin
    //don't bother checking for errors since we don't need to know if it fails
    SetProcessDEPPolicy(PROCESS_DEP_ENABLE);
  end;
end;

这将适用于任何版本的Delphi。

您无法在运行时设置ASLR标志,因为它会影响模块的加载方式。因此只能使用PE标志来设置ASLR。

修改非常旧版本的Delphi的PE标志

较早版本的Delphi不支持$SetPEFlags$SetPEOptFlags。对于此类版本,您需要使用外部工具来修改可执行的生成后版本。当我最初编写此答案时,我假设来自MS工具链的EDITBIN可以胜任。对于DEP,使用/NXCOMPAT选项就足够了。对于ASLR,您将需要使用其他PE标志编辑器。我的网络搜索显示来自cygwin的peflags

1
peflags --dynamicbase=true --nxcompat=true MyApp.exe

我确定还有其他PE标志编辑选项可用。


" {$ DYNAMICBASE ON}"是Delphi2007中的新功能," {$ SETPEOPTFLAGS $ 40}"是现有的指令:info

{$ SetPEOptFlags $ 40}在Delphi2006中工作