Click to See Complete Forum and Search --> : Problem with __fastcall & __cdecl calling conventions
Hi all,
I've a project (in face 2 projects), that I've to integerate with other project. One of the project is build with __fastcall calling convention, where as the other has been developed with __cdecl.
Actually, the second one is some third party library and do not support __fastdecl, where as the first one is developed by someone else (who developed it with __fastdecl).
When I try to put the functions of the second library (which support __cdecl only), such that I make the calling convention of the first project as __fastcall and the files of the other project (these are .c files) as __cdecl, I get linking errors (like error LNK2001: unresolved external symbol @msleep@4)
I like to ask, what is the proper way of doing that, any reference, pointers, suggestions will be highly appriciated.
Thanx
jonnin
10-04-2004, 08:04 AM
you need to wrap the header file for the c lib in an
extern "C" {} statement for starters.
Second, know the difference between the calling types and if your compiler cannot emulate one of them, you may have to use assembly language to finish up the function returns (the differences are usually where parameters are when the function terminates, whether the function is responsible for the stack or the caller is, etc)
Thanx for the reply jonnin,
let me elaborate my situation a little more.
Some other team developed a project with __fastcall calling convention. It works very well, but now, it is required to integrate a third party library with it, the entire library's source code is provided but the library only support __cdecl (I've confirmed from the third party as well and they notified that there library do not support __fastcall and support only __cdecl).
The original project that I've, include some .obj files (I don't have the entire source code, coz I'm not the part of that team who developed that, so I don't need to know about that code, based on that reason, I've header files and object files in the project).
Now, if I set __cdecl for the entire project and compile, I get linking error (for e.g. like error LNK2001: unresolved external symbol @msleep@4) in the object file being created of the third party source files.
I've put the question to my team lead that is it possible to compile the source of original project with __cdecl rather then __fastdecl, so that the conflict between the two can be resolved, but haven't got the answer so far.
What is your opinion about that? Any idea, reference, pointer, suggestion etc will be highly appriciated & thanx in advance.
Best Regards,
Ejaz.
Danny
10-04-2004, 09:51 AM
if you change the caloing convention in the header file, you need to make sure that the binaries files are created from source files that use the same calling convention. In other words, you can't change the header files while using the original .obj or .lib files. So you have to options: get the original source files and recompile them with the __cdecl calling convention or switch to a compiler that supports __fastcall. It may be possible, as jonnin suggests, to simulate __fastcall by tampering with the assembly code or by setting a few compiler switches that enforce argument passing through registers. However, this is a very brittle solution so you want to try the first two options.
Dear Danny,
Thanx for ur suggestion, I read at some site that __fastcall does make difference at 386/486 machines, but with latest machines, there is not much difference in using __fastcall & __cdecl. The project will be running at the most updated machines.
Also, I'm expected to provide the results shortly and havent't used assembly after academacis. Please give me advice, is it fine to go with __cdecl or investment at assembly will be worthwhile?
Looking forward for your suggestions.
Regards,
Ejaz.
Danny
10-04-2004, 04:55 PM
the question is not whether this makes a difference or not with respect to performance; the calling convention affects the linkage of these functions so you can't link a binary file that was compiled with __fastcall to another file that was compiled with the __cdecl call. The signatures of such functions are incopatible and that's why you're having linkage errors. As for performance, __fastcall was a duff hack that allegedly added a few grains of speed to the executable, especially in the Olden Days. Today it's at best, a useless feature that doesn't hurt. So again, if you can recompile everything (I mean not just the header files but also the .cpp files) with _cdecl, go ahead and forget about __fastcall.
jonnin
10-04-2004, 05:10 PM
that error looks like a C to CPP name mangle error to me. If you have a calling convention error, it should be different error? I'm not sure, I haven't had a mixed language error in some time, not since I converted the other stuff to a dll, which would also cure you if you only had all the source... did you try the extern wrapper (it can't hurt you, but if I am correct, you may get to move on)?
Thanx alot guys, I hope I'll move on very well.
devx.com
Copyright Internet.com Inc. All Rights Reserved