ocienvcreate php 失败_MS VC链接器(link.exe):为什么没有关于32/64位CPU体系结构不匹配的警告?...

(Update: As per Hans' suggestion, here's a suggestion to improve link.exe's behaviour, and you can vote for it if you have an account over there.)

Okay, I'm a fool. In January I installed Oracle on my computer, Win7 Pro 64 Bit. I installed the 64 Bit version. Yesterday, using MSVC Express, I tried to compile and link a small test programm oci1.c against oci.h and oci.lib.

cl /nologo /c /I%ORACLE_HOME%\oci\include oci1.c

link /nologo oci1.obj /LIBPATH:%ORACLE_HOME%\oci\lib\msvc oci.lib

My attempts kept failing with LNK2019, which means unresolved external symbol 'symbol' referenced in function 'function'. The symbol in question (_OCIEnvCreate) is, of course, provided by oci.lib, so the linker should be able to resolve it.

It finally dawned on me that it couldn't work because my compiler is 32 bit only, and the import library is 64 bit. If you're a fool and you don't know or remember, then you can see it using the dumpbin utility:

$ dumpbin /headers %ORACLE_HOME%\oci\lib\msvc\oci.lib | head

File Type: LIBRARY

FILE HEADER VALUES

8664 machine (x64)

$ dumpbin /headers oci1.obj | head

File Type: COFF OBJECT

FILE HEADER VALUES

14C machine (x86)

So far, so good. But I wasted some time and would like to avoid repeating that experience.

While not incorrect, the LNK2019 error message doesn't lead you straight in the right direction. There's no warning that you're attempting to link binaries for different CPU architectures.

Note that when you specify the X64 architecture, you are alerted to the fact that you specified X86 binaries:

$ link /machine:x64 /nologo oci1.obj /LIBPATH:%ORACLE_HOME%\oci\lib\msvc oci.lib

oci1.obj : fatal error LNK1112:

Modul-Computertyp "X86" steht in Konflikt mit dem Zielcomputertyp "x64".

But there is no such precise warning when you specify the X86 architecture, explicitly or implicitly:

$ link /machine:x86 /nologo oci1.obj /LIBPATH:%ORACLE_HOME%\oci\lib\msvc oci.lib

oci1.obj : error LNK2019: Verweis auf nicht aufgelöstes externes Symbol

"_OCIEnvCreate" in Funktion "_main".

oci1.exe : fatal error LNK1120: 1 nicht aufgelöste externe Verweise.

I just found the /VERBOSE switch to link.exe, which when used hints that no symbols are found in my 64 bit oci.lib.

Are there other options you can turn on to make the linking process more, eh, fool-proof?

Update: As per Hans' answer, I ran dumpbin on a 32 bit import library, and the names appear as follows:

$ dumpbin /exports D:\Opt\MySQL5.5\lib\libmysql.lib

_load_defaults

_myodbc_remove_escape@8

_mysql_affected_rows@4

_mysql_autocommit@8

_mysql_change_user@16

_mysql_character_set_name@4

Whereas the names in the 64 bit OCI import library that I'm dealing with here appear undecorated:

OCIXmlDbFreeXmlCtx

OCIXmlDbInitXmlCtx

ORLRconNativeInt

ORLRvalNativeInt

OraCoreIsPhysicalRawFile

OraMemAlloc

When compiling for the x64 architecture in a Windows context (whether

using Microsoft or non-Microsoft tools), there is only one calling

convention — the one described here, so that stdcall, thiscall, cdecl,

fastcall, etc., are now all one and the same.

Makes sense to me now. One and only calling convention, hence no name mangling necessary, hence no leading underscore as per cdecl when compiling for X86.

解决方案

I think it simply complains about the missing symbol before getting around to checking the binary compatibility. That will commonly happen first, x64 symbols don't have the leading underscore since x64 doesn't have any calling conventions. Unless you use Microsoft import libraries, they don't decorate the symbols at all.

But I very much agree, getting the compatibility error first would be much more productive. No idea how hard that is to implement. Ask the guys who know and can make it work like that, post a feature request to connect.microsoft.com

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值