4

编译时,我总是将其设置为 Any CPU。然而,有些客户没有所需二进制文件的 64 位版本,即使在 x64 系统上运行时也是如此。在这些情况下,我要求他们使用 corflags.exe /32BIT+ 选项修改我的二进制文件:

http://msdn.microsoft.com/en-us/library/ms164699(VS.80).aspx

如果 64 位版本不存在,我想让它透明并在安装期间自己修改二进制文件。我不希望自己调用 corflags.exe,因为这意味着我需要重新分发应用程序,这在我们的运输要求中是不允许的。

所以我的问题是;有没有办法自己以编程方式修改这个标志,或者直接修改二进制文件(它只是在文件本身的某处设置一个字节)?

4

4 回答 4

3

我还没有尝试过,但是您是否能够在二进制副本上运行 corflags 并执行二进制 diff 以确定修改了哪些偏移量。您可以将其作为安装脚本的构建操作来执行,并将偏移量存储在安装程序中。

在安装时只需根据需要更改偏移量。

当然,我永远不会支持这样的行为,只是说'

;-)

顺便说一句,如果您不断需要将程序集标记为 32 位,您可以考虑只针对该平台而不是事后将其更改为 32 位。

干杯。

于 2009-06-02T04:16:20.817 回答
1

为什么不专门为两种架构(32 位和 64 位)构建您的程序集,将两者都包含在您的安装程序中,然后在安装时检测您的客户端拥有的此依赖程序集的哪个版本,然后安装适当的架构版本你的申请。这样,手动修改二进制文件或需要在安装程序中包含 corflags 就不会搞砸了。

于 2009-06-02T03:44:39.777 回答
1

对于文件本身,我相信(尚未确认)您可以自己修改 IMAGE_COR20_HEADER。只需设置 MinorRuntimeVersion 就可以了。这是关于如何使用 IMAGE_COR20_HEADER 来确定加载哪个运行时的(有些过时的)解释:http: //blogs.msdn.com/joshwil/archive/2004/10/15/243019.aspx

为什么不总是为 x86 编译,64 位运行时会给您带来什么好处?

请注意,某些代码(interop/P/invoke)只能在 32 位或 64 位运行时中工作,因此仅将相同的程序集加载到另一个运行时中是行不通的。

编辑:快速而肮脏的示例来读取 IMAGE_COR20_HEADER:

_pDosHeader = reinterpret_cast<PIMAGE_DOS_HEADER>(_pFileBase);
_pNTHeader = reinterpret_cast<PIMAGE_NT_HEADERS>(_pFileBase + _pDosHeader->e_lfanew);
_pFileHeader = reinterpret_cast<PIMAGE_FILE_HEADER>(&_pNTHeader->FileHeader);
_pOptionalHeader = reinterpret_cast<PIMAGE_OPTIONAL_HEADER>(&_pNTHeader->OptionalHeader);
IMAGE_DATA_DIRECTORY const* entry = NULL;
entry = &pOptionalHeader->DataDirectory[IMAGE_DIRECTORY_ENTRY_COMHEADER];
if (entry->VirtualAddress == 0 || entry->Size == 0  || entry->Size < sizeof(IMAGE_COR20_HEADER)) {
return E_FAIL;
}
pClrHeader = reinterpret_cast<IMAGE_COR20_HEADER*>(RtlImageRvaToVa32(_pNTHeader, _pFileBase, entry->VirtualAddress, 0));

不相信这是一个好主意,但将其作为安装程序步骤。

于 2009-06-02T00:51:59.353 回答
0

如果您可以在安装过程中检测到这一点,为什么不直接从安装程序中运行 corflags.exe?这对我来说听起来好多了,而不是尝试自己更改二进制数据。

于 2009-06-02T02:40:41.367 回答