I'm trying to take advantage of some of OpenSSL's EC cryptography and ECDSA functionality to make a rudimentary blockchain simulation, but I've run into a major roadblock. I'm using the Code::Blocks IDE, and I've installed OpenSSL using the 64-bit binary found here: https://slproweb.com/products/Win32OpenSSL.html.
In Linker Settings, I added OpenSSL-Win64\lib\openssl.lib
In Search Directories > Compiler, I added OpenSSL-Win64\include
In Search Directories > Linker, I added OpenSSL-Win64\lib
However, when I compile, I get the "undefined reference to (function name)" error for every OpenSSL function I try to use. However, the compiler seems to be successfully including the header files, since it recognizes the new data types like EC_KEY. I suspect a linking error, but I'm not sure what could be wrong, since I have the link paths and static library linked as above.
Here is my build log:
mingw32-g++.exe -LD:\OpenSSL-Win64\lib -LD:\OpenSSL-Win64\include -LD:\OpenSSL-Win64 -o bin\Debug\BlockchainSim.exe obj\Debug\main.o obj\Debug\src\Block.o obj\Debug\src\BlockchainNode.o obj\Debug\src\Transaction.o obj\Debug\src\Valuable.o D:\OpenSSL-Win64\lib\openssl.lib
obj\Debug\src\BlockchainNode.o: In function `ZN14BlockchainNodeC2Ei':
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:18: undefined reference to `EC_KEY_new_by_curve_name'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:21: undefined reference to `BN_new'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:22: undefined reference to `EC_KEY_set_private_key'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:25: undefined reference to `BN_CTX_new'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:26: undefined reference to `BN_CTX_start'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:28: undefined reference to `EC_KEY_get0_group'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:29: undefined reference to `EC_POINT_new'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:30: undefined reference to `EC_POINT_mul'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:31: undefined reference to `EC_KEY_set_public_key'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:34: undefined reference to `EC_POINT_free'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:35: undefined reference to `BN_CTX_end'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:36: undefined reference to `BN_CTX_free'
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:37: undefined reference to `BN_clear_free'
obj\Debug\src\BlockchainNode.o: In function `ZN14BlockchainNodeD2Ev':
F:/School/Barrett/BlockchainSim/src/BlockchainNode.cpp:42: undefined reference to `EC_KEY_free'
collect2.exe: error: ld returned 1 exit status
Process terminated with status 1 (0 minute(s), 0 second(s))
15 error(s), 0 warning(s) (0 minute(s), 0 second(s))
I'm hoping I'm just missing something simple here since I'm new to linking static libraries. A lot of similar issues seem to be solved by adding options to compile commands, but since I'm using Code::Blocks and linking OpenSSL as a static library, I'm not sure if those apply here. Any help is greatly appreciated.
Figured it out. The issue was that I had no C:/MinGW folder (as Code::Blocks installed MinGW within its own directory). I'm guessing the binary I used tries to detect existing compilers and compiles the library differently depending on what it finds.
I fixed it by installing default MinGW (with MSYS, in case that matters) with the default path (C:/MinGW) and then reinstalling the 32-bit binary OpenSSL linked in the original question, also in the default path (C:/OpenSSL-Win32). This made it so that within the C:/OpenSSL-Win32/lib folder, there was a new MinGW folder which I then included in the linker search directories.
Related
I'm building a golang project by using Go1.12 + msys2/mingw-w64(9.2.0), it shows errors:
D:\Go\pkg\tool\windows_amd64\link.exe: running gcc failed: exit status 1
D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/lib/../lib/crt2.o: in function `pre_c_init':
E:/mingwbuild/mingw-w64-crt-git/src/mingw-w64/mingw-w64-crt/crt/crtexe.c:146: undefined reference to `__p__fmode'
D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/lib/../lib/crt2.o: in function `__tmainCRTStartup':
E:/mingwbuild/mingw-w64-crt-git/src/mingw-w64/mingw-w64-crt/crt/crtexe.c:290: undefined reference to `_set_invalid_parameter_handler'
D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: E:/mingwbuild/mingw-w64-crt-git/src/mingw-w64/mingw-w64-crt/crt/crtexe.c:299: undefined reference to `__p__acmdln'
D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/lib/../lib/libmingw32.a(lib64_libmingw32_a-merr.o): in function `_matherr':
E:/mingwbuild/mingw-w64-crt-git/src/mingw-w64/mingw-w64-crt/crt/merr.c:46: undefined reference to `__acrt_iob_func'
D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/lib/../lib/libmingw32.a(lib64_libmingw32_a-pseudo-reloc.o): in function `__report_error':
E:/mingwbuild/mingw-w64-crt-git/src/mingw-w64/mingw-w64-crt/crt/pseudo-reloc.c:149: undefined reference to `__acrt_iob_func'
D:/msys64/mingw64/bin/../lib/gcc/x86_64-w64-mingw32/9.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: E:/mingwbuild/mingw-w64-crt-git/src/mingw-w64/mingw-w64-crt/crt/pseudo-reloc.c:150: undefined reference to `__acrt_iob_func'
collect2.exe: error: ld returned 1 exit status
After some research I'm sure it's a msvcrt compatibility issue of mingw64.
I know there are workarounds like this: unresolved external symbol __imp__fprintf and __imp____iob_func, SDL2
But it doesn't solve all of my issues.
I try to link the library: LDFLAGS: -L%filepath% -llegacy_stdio_definitions, nothing changes.
Is there a patch to fix it, or do I have to build my custom version of mingw64?
So I answer my question by myself, the case is closed.
Yes, Mingw64 uses msvcrt.
Here are some tips that could help to solve dependency problems between Mingw64 & msvcrt.
The major goal is to let compiler load the correct version of MSVCRT library family.
1.Update Mingw64.
2.Check out MSVCRT_VERSION in Mingw64\include_mingw.h(or x86_64-w64-mingw32\include), make sure the version number matches your windows version, or modify it.
3.Take a look at linker option like "#cgo LDFLAGS: -Lxxx", don't mess the library path. Remove any unnecessary library path setting, let linker finds libraries itself.
Make sure everything is built with same libraries.
This is probably related to
c++ reading fits file using ccfits
which was never answered.
Anyway, I hope my question is easier to reproduce. There is an example program for CCfits at:
http://heasarc.gsfc.nasa.gov/fitsio/CCfits/html/cookbook.html
I am attempting to compile this using:
g++ cookbook.cpp -o cookbook -lCCfits -lcfitsio
The link fails for every CCfits function in the file:
/tmp/cc7hVaju.o: In function main':
cookbook.cpp:(.text+0x14): undefined reference towriteImage()'
cookbook.cpp:(.text+0x31): undefined reference to writeAscii()'
cookbook.cpp:(.text+0x4e): undefined reference towriteBinary()'
cookbook.cpp:(.text+0x6b): undefined reference to copyHDU()'
cookbook.cpp:(.text+0x88): undefined reference toreadHeader()'
cookbook.cpp:(.text+0xa5): undefined reference to readImage()'
cookbook.cpp:(.text+0xc2): undefined reference toreadTable()'
cookbook.cpp:(.text+0xdf): undefined reference to readExtendedSyntax()'
cookbook.cpp:(.text+0xfc): undefined reference toselectRows()'
collect2: error: ld returned 1 exit status
I have tried this with the CCfits package that comes with Ubuntu. I have also tried installing the package myself. Same error.
Strangely, I get similar messages if I do not include the libraries on the command line (i.e., "g++ cookbook.cpp -o cookbook"). The one difference is that I also get this error:
/tmp/ccMVMkSB.o: In function CCfits::FITS::setVerboseMode(bool)':
cookbook.cpp:(.text._ZN6CCfits4FITS14setVerboseModeEb[_ZN6CCfits4FITS14setVerboseModeEb]+0xf): undefined reference toCCfits::FITS::s_verboseMode'
This must be a clue, right? Seems to say that the libraries I have named, although they exist, do not contain all the functions I need.
Thanks for any help,
Charles
Not sure if you got a suitable answer to this question but as far as I can tell the main issue is that you are not including the definitions to the function signatures. These are usually defined in the header files of c++ libraries.
For example, if your library is installed in "/usr/local" on a UNIX system then the header files will be installed in the location "/usr/local/include/CCfits". The corresponding lib files will be installed at "/usr/local/lib". The important thing is that the compiler does not know this and you need to inform it of these locations.
g++ cookbook.cpp -o cookbook -I /usr/local/include/CCfits -L /usr/local/lib -lCCfits -lcfitsio
The "-I /usr/local/include/CCfits" flag and the given parameter inform g++ of the location of the header files that it is looking for. The "-L /usr/local/lib" flag and the given parameter inform g++ of the location of the library files. It is important to note that g++ will search in the standard location for libraries on in your environment as well this is just giving it more locations to search. There are in fact rules for what it should do if it finds multiple libraries which are the same in different locations but I don't explicitly remember those.
Also to be safe, ensure that the libraries are loaded into memory by the OS. These are shared libraries not static so they are not stored into the executable file. This won't make a difference when compiling the source but will prevent the successful execution of the executable. To ensure that the OS has loaded the library into memory run the following command:
sudo ldconfig
Yours Aye,
Omar EQ
Recently I found an example of how to use the expect library in C++. I tried to compile it, but the compiler (g++) said, that tcl8.5/expect.h doesn't exists. So I tried to include tcl8.6/expect.h - still the same error. I checked the /usr/include/ directory and I wasn't surprised when I've noticed, that there is no tcl8.x directory.
I've searched for files with "expect" in their name. Here's what I found:
/usr/include/expect_tcl.h
/usr/include/expect_comm.h
/usr/include/expect.h
Unfortunately when I tried to include any of these I got the following list of errors during compilation:
> g++ test.cpp -Wall -std=c++0x -ltcl8.6 -lglog -o test
/tmp/cce8k1BA.o: In function `task(std::string const&, std::string const&, std::string const&)':
test.cpp:(.text+0x16): undefined reference to `exp_is_debugging'
test.cpp:(.text+0x20): undefined reference to `exp_timeout'
test.cpp:(.text+0x38): undefined reference to `exp_popen'
etc...
How can I solve this problem?
[EDIT]
When I tried to link it with the expect lib (-lexpect) I got the following error:
/usr/bin/ld: cannot find -lexpect
collect2: error: ld returned 1 exit status
I'm sure that both - tcl8.6 and expect 5.45-4 are installed.
The usual way of distributing Expect these days puts the shared library in a non-standard location and loads it dynamically by full pathname. This works well and is minimal fuss for most people, but does make it rather hard to use Expect's C interface in your own code.
The easiest way is going to be to build your own copy from source, especially as that will give you control over how exactly it was built. This can particularly include keeping the majority of symbols in the library instead of stripping them on install, which will help a lot with debugging. You probably ought to use the current supported version. (Yes, it's a release from several years ago. It doesn't need a lot of support effort most of the time.)
You haven't linked to the expect library during your build. Add -lexpect to your g++ command.
I am getting a compile error trying to compile a simple tester program from the documentation.
C:\DOCUME~1\A\LOCALS~1\Temp\ccRsXzHu.o:tester.cpp:(.text+0xa6): undefined reference to `_imp___ZN5boost6thread4joinEv'
C:\DOCUME~1\A\LOCALS~1\Temp\ccRsXzHu.o:tester.cpp:(.text+0xb4): undefined reference to `_imp___ZN5boost6threadD1Ev'
C:\DOCUME~1\A\LOCALS~1\Temp\ccRsXzHu.o:tester.cpp:(.text+0xcf): undefined reference to `_imp___ZN5boost6threadD1Ev'
C:\DOCUME~1\A\LOCALS~1\Temp\ccRsXzHu.o:tester.cpp: (.text$_ZN5boost11this_thread18interruptible_waitEy[boost::this_thread::interruptible_wait( unsigned long long)]+0x4a): undefined reference to `_imp___ZN5boost11this_thread18interruptible_waitEPvNS_6detail7timeoutE'
C:\DOCUME~1\A\LOCALS~1\Temp\ccRsXzHu.o:tester.cpp: (.text$_ZN5boost6threadC1IPFvvEEET_NS_10disable_ifINS_14is_convertibleIRS4_NS_6detail13thre ad_move_tIS4_EEEEPNS0_5dummyEE4typeE[boost::thread::thread<void (*)()>(void (*)(), boost::disable_if<boost::is_convertible<void (*&)(), boost::detail::thread_move_t<void (*)()> >, boost::thread::dummy*>::type)]+0x23): undefined reference to `_imp___ZN5boost6thread12start_threadEv'
collect2: ld returned 1 exit status
I am using mingw 4.5 and g++ 4.5.2 on windows. Boost version v1.4.8.
I hope someone can help me solve this problem.
Thanks.
It looks like you aren't linking to the boost libraries.
Boost doesn't come with windows since it isn't a standard library. You've got to download the headers and libraries, then include the headers in your project and link to the libraries at compile time. Since you're using g++, this means adding a -l line to your compile command. The -l line must be used with each specific library you want to use also, you can't just specify the boost directory.
This page will help you get started on Windows and this page will help you get started on *nix platforms.
Once you've compiled boost, then in your example, you should compile your program with
g++ -o tester.exe -Lpath/to/boost/libraries/ -lboost_thread tester.c
Make sure you've got all your libraries linked properly.
Try putting this line first if your thread library is statically defined
#define BOOST_THREAD_USE_LIB
Also, check out this thread.
I'm trying to set up libusb API on my OS. I downloaded libusb api on libusb.org. I followed the standard installation procedure:
cd into directory
./configure
make
make check //without errors
make install
Then I launched Eclipse C/C++ and copied some code from the tutorial found on the internet. But when trying to build it I got following output:
main.cpp:(.text+0x19): undefined reference to `libusb_init'
main.cpp:(.text+0x76): undefined reference to `libusb_set_debug'
main.cpp:(.text+0x8a): undefined reference to `libusb_get_device_list'
main.cpp:(.text+0x136): undefined reference to `libusb_free_device_list'
main.cpp:(.text+0x142): undefined reference to `libusb_exit'
/tmp/ccOWJGwe.o: In function `printdev(libusb_device*)':
main.cpp:(.text+0x162): undefined reference to `libusb_get_device_descriptor'
main.cpp:(.text+0x28a): undefined reference to `libusb_get_config_descriptor'
main.cpp:(.text+0x4d4): undefined reference to `libusb_free_config_descriptor'
collect2: ld returned 1 exit status
I have libusb.so in /lib and also I have usb.h in /usr/local/include and the link for the .so and libusb.a in /usr/local/lib.
Also the #include inside the code is correct.
I know that problem is in linker but I, kind of, cannot make it work :)
I'm using Fedora 15 operating system and gcc 4.6.0 20110603 (Red Hat 4.6.0-10) version compiler.
So what could I do to resolve these undefined references? Thanks very much for help :)
I did face the same problem. But I was able to solve it by adding '-lusb-1.0' to the linker.
e.g : g++ myfile.cpp -lusb-1.0
you have to set the library linker flag for compilation in the linker,
you can get a full list in the console by executing
pkg-config --list-all
These are the libraries which you have installed on your system and you have to link against the ones you want to use.
so in your example it is libusb so you do
pkg-config --libs libusb
there should be the output
-lusb
or
-lusb-1.0
This gives you the flag you have to pass to the linker. e.g.
g++ myfile.cpp -lusb[-1.0]
Then you edit the configuration of the project and search for the linkerflags, there should be a textfield for that somewhere in the buildoptions. i'm not quite shure where to find it but googling for it suggested:
Project -> Properties -> C/C++
Build -> Miscellaneous -> flags
After you found it, just add the linker flag in the textfield and you should be fine.
EDIT
since my answer is the accepted one, I also added the other flag that seems to work for a lot of people.
What is your linker command line? You need to have -lusb in the linking command; just having the header included won't work.
I don't use Eclipse C/C++ but I am pretty sure the reason is the same that I faced some while ago when setting up a C project in Netbeans.
It's not enough to have the #include in your code and the library at the right location - you also have to tell Eclipse where to look for them and how to use them. This turorial shows you how to set it up in Eclipse.