a couple days ago, the boss asked me to convert a C++ project from X86 to X86_64. I thought it is easy for me, just do two the following steps:
- 1. replace all of the x86 libraries (SO)to their counterparts of x86_64
- 2. change the compile option from -m32 to -m 64
After that, I tried to make the project. it ended with the following error: libcommonldap.so: undefined reference to `NewDecryptStr(char*, unsigned int)
It is a usual link error. Using objdump to check if this symbol is there.
[root@centos src]# objdump -t output/libsupport.so | grep NewD
00000000000123af g F .text 00000000000000e7 _Z13NewDecryptStrPcm
Yes, it is there. but why ld can not find it? I konw the symbol _Z13NewDecryptStrPcj is what I wanted. The wired name is caused by c++ name mangling. But why the ld does not recognize it? What the ld really wants? Using objdump again to check:
[root@centos src]# objdump -t output/libcommonldap.so | grep NewD
0000000000000000 *UND* 0000000000000000 _Z13NewDecryptStrPcj
int NewDecryptStr(char *sEncryptedPassword, const size_t sizeof_sEncryptedPassword)
I decoded the two symbols as follows:
NewDecryptStr(char*, unsigned long)
[root@centos commonsource]# c++filt _Z13NewDecryptStrPcj
NewDecryptStr(char*, unsigned int)
[root@centos commonsource]#
#ifndef size_t
#define size_t unsigned int
#endif
It is true for x86, but for x86_64, size_t should be ULONG. This is the reason