I'm facing the error when I'm linking an external library and code with the current project. You will understand the problem by this example.
//foo.h
namespace LMS
{
class foo
{
foo(); //implementation in cpp
foo(int dummy) //implemented here
{
//something
}
};
} // namespace LMS
//foo.cpp
#include"foo.h"
namespace LMS
{
foo::foo()
{
//something
}
} // namespace LMS
//externalProgram.h
#include "foo.h"
LMS::foo *ptr;
ptr = new LMS::foo(); //Linking error: LNK 2019
ptr = new LMS::foo(2); //No error
Now the problem is that the external program doesn't know about the foo.cpp and the implementation of class foo methods in it. I'm currently using VS2019 and using two projects in the same solution. I've tried several ways to correct this but it didn't work out. The current way I'm seeing is to implement all the functions in header files.
EDIT: I've already linked the files!!
You should be able to mark your externalProgram project as dependent on the foo project. This will link foo.o in with external program.
Using the UI you will select this in
Project > Project Dependencies : Depends on ...
If that is correct, then the problem is more subtle, sometimes just a simple typo. At this point you want to use the command line tools to break apart the library and confirm the object files, and break apart the object files and confirm the symbols within. A ten year old SO posting discusses using lib.exe to example the library file. The dumpbin tool has a /symbols option that might also be handy for looking at the actual code generated.
Related
I wish to unit test my code. It is a proprietary step in a task I have, the code of which I already wrote.
I am using VS Community 2017 v.15.9.7. I have followed the instructions of this site to the utmost detail, line by line:
https://blogs.msdn.microsoft.com/vcblog/2017/04/19/cpp-testing-in-visual-studio/#Setup
But after all the includes I get two errors :
1) Error LNK1120 1 unresolved externals UnitTest1 \source\repos\Primes\Debug\UnitTest1.dll 1
2) Error LNK2019 unresolved external symbol "public: bool __thiscall SearchPrimes::IsPrime(int)" (?IsPrime#SearchPrimes##QAE_NH#Z) referenced in function "public: void __thiscall UnitTest1::TestClass::IsOdd(void)" (?IsOdd#TestClass#UnitTest1##QAEXXZ) UnitTest1 C:\Users\Velzevoul\source\repos\Primes\UnitTest1\unittest1.obj
I have tried moving files, but I thing randomly moving them around will do more harm than good. I read about including the "stdafx.h" to my "source", but that made thing worse, as more errors kept popping up.
Here are the header files of the code I wrote:
#pragma once
#include <vector>
#include "XMLParser.h"
class SearchPrimes
{
public:
std::vector<int> RangePrime(const std::pair<int, int>&);
//Setting the range to search for prime numbers, executing the algorithm
bool IsPrime(int); //The algorithm that checks if a number is prime
bool IsOdd(int); //Checking if a number if even or odd
};
#pragma once
#include <iostream>
#include <vector>
class XMLParser
{
public:
void removeTags(std::string&); //Removing the brackets of the tags of the .xml
std::string openFile(std::string); //Opening a file
std::vector<std::string> readFile(const std::string&, std::string);
//Getting the text from the .xml file to a vector
std::vector<std::pair<int, int> > stringsToInts();
//Finding the values of the tags that contain the ranges
//and converting the string numbers to a vector<int>
};
Here is the test.cpp
#include "stdafx.h"
#include "CppUnitTest.h"
#include "/Users/Velzevoul/source/repos/Primes/Primes/SearchPrimes.h"
#include "/Users/Velzevoul/source/repos/Primes/Primes/XMLParser.h"
using namespace Microsoft::VisualStudio::CppUnitTestFramework;
namespace UnitTest1
{
TEST_CLASS(TestClass)
{
public:
TEST_METHOD(IsOdd)
{
SearchPrimes prime;
Assert::IsTrue(prime.IsPrime(4));
}
};
}
What do I have to do in order to solve the external dependencies? The article says, that once I follow the steps I can begin. The test is in a separate project, as the article suggests. If you think that the problem may be related to my main() function, please tell me to include it. I do not right now, because it's quite lengthy.
I thank you for your time in advance!
That article is suggesting that you can just link to a Windows executable the same way you would a DLL. I suppose this is theoretically be possible if your executable has been set up to export its functions, but it seems like an odd thing to do.
There are two options for accessing the code under test in a C++ unit test project:
Add the source modules (.cpp/.h) to your unit test project.
Link with a library containing the code.
If your project is relatively simple, with just a few .cpp modules, then option 1 is probably the way to go. Right-click your unit test project, select "Add -> Existing Item..." and add the .cpp modules you want to test.
For a more complex project with many source modules, option 2 might be a better option. Create one or more library projects (static or dynamic) to contain your source modules, then link both the executable and unit test projects with the library.
A good practice is to create one unit test project for each project to be tested. Give the unit test project a name that indicates what project it is testing, i.e. MyExecutable and MyExecutable.Test, MyLibrary and MyLibrary.Test, etc.
I'm new to cpp in eclipse and trying to mess with simple builds. I have made a basic project which automatically generates build info (no user-defined makefile).
Simple (Working) Case
I made a "Hello World" project called Test (not an empty project). It has one file - Test.cpp with a main() in => builds and runs fine.
Test.cpp
int main() {
// output some stuff
}
Slightly More Complex (Working) Case
I make a new file called Main.cpp. Move the main() function into Main.cpp and make a decleration of a function in main too - void test();
The test() function lives in Test.cpp, which is where I provide the function definition.
Main.cpp
#include <iostream>
void test();
int main() {
// Use test()
}
Test.cpp
#include <iostream>
void test() {
// output some stuff
}
Build it, there are now two .o files in the Debug directory - Test.o and Main.o. This runs fine.
The Problem
Now I try to introduce a third file - Limits.cpp.
Limits.cpp
#include <iostream>
void printLimits() {
// Print out limits for different integer sizes
}
Again I provide a deceleration of this function in Main.cpp.
Main.cpp
#include <iostream>
void test();
void printLimits();
int main() {
// Use printLimits()
}
This time there is no object file created for Limits in the Debug folder => the build fails.
Main.cpp:*line* undefined reference to `getLimits()'
It just looks like the autogenerated build config for the project is duff. I've tried looking around the project properties but I have had no luck. I've tried including the path/file in Include Paths/Include files, other objects, and I've checked just about every other property I can see. This has been frustrating me for two days.
The strange thing about this is case 2. It looks like because Test.cpp was the first file made it always includes this in the build? (even if it is not imported). Where as because Limits.cpp is new and not imported it doesn't generate an object file so it can't link the function.
I could me making an error by needing to include the files but my understanding is if all the object files make it to the linker then all will be well (ie I just need the function declarations when making the object files which is what I have here).
With a "Blank project" it seems to compile all the cpp files even if they are never used so my case above works. (Although, it doesn't work for files in subfolders of src). Looks like its a "feature" of the "Hello world" project type but it's going to drive me crazy knowing there must be a way to get it to do this.
If anyone knows if it is possible to include this file without writing my own makefile (I'm not a makefile guru (yet!)), or let me know if this is not possible with autogen CDT that would be great.
Using MinGW GCC toolchain.
Thanks
Ok, I am very new in C++ development. This question may be silly but I can not find its response in any tutorial, book, question/response. It would be great if somebody can kindly explain it to me.
I have 1 header-source pair inside of a shared library libdummy.so:
This is dummy.h:
class dummy
{
public:
~dummy();
dummy();
bool dosomething(int a);
};
and this is dummy.cpp:
#include "dummy.h"
dummy::dummy()
{
//some assignments here
clear();
}
dummy::~dummy()
{
clear();
}
bool dummy::dosomething(int a)
{
// do something here
return true;
}
EDIT: I tell you above the sample codes of dummy.h and dummy.cpp but these files are not in my hand. They are packed inside the library libdummy.so. I have only the libdummy.so shared library file in the hand.
And I have a client to access my shared library.
client.h is here:
#include "dummy.h"
class client
{
public:
void myownjob();
dummy thingy;
//and some functions here
};
and finally this is the client.cpp:
#include "client.h"
void client::myownjob()
{
thingy.dosomething(1);
}
Now my problem is; when I try to compile this code, I get undefined reference errors to the constructor and destructor:
error: undefined reference to 'dummy::~dummy()'
error: undefined reference to 'dummy::dosomething(int)'
error: undefined reference to 'dummy::dummy()'
EDIT: The dummy.h and dummy.cpp are inside libdummy.so. I have only 3 files in the hand: libdummy.so, client.h and client.cpp.
That's why;
I can not delete ~dummy(); and dummy(); in the dummy.h to let the compiler creating them automatically. Because dummy.h is inside the libdummy.so shared library. It is not directly editable.
I can not do some braceleted empty definitions like ~dummy(){} and dummy(){} in the dummy.h. Because dummy.h is inside the libdummy.so shared library. It is not directly editable.
I can not include dummy.cpp to SRC_FILES line of my makefile. Because dummy.cpp is inside libdummy.so shared library. It is not a seperate file.
I think this is a very simple/beginner problem, but I can not find its response anywhere. What I have to do to use a class which is inside a shared library, in C++, when I get undefined reference errors to the constructors and destructors?
Thanks in advance.
I don't know about any NDK, but this error is a linking error - where you don't provide the library at link time (even though it's a dynamic library, you have to provide it when linking)
Normally I'd tell you to compile + link like this:
g++ client.cpp -ldummy
(-ldummy links with libdummy.so)
but given you're using some makefile you're not familiar with, I don't really know how you should do it. I can guess though:
Apparently you have a field named SRC_FILES. A quick (and incomplete) google suggest you have a field named LOCAL_LDLIBS. If so try setting this:
LOCAL_LDLIBS = -ldummy
Or, if the libdummy.so file isn't in your standard path:
LOCAL_LDLIBS = -L/dummy/file/path -ldummy
(/dummy/file/path is obviously the path of your dummy library)
Note that depending on your configuration, you might need to add the -L even if the file is in your working directory.
please compile both the file.. If you are using linux , than
g++ client.cpp dummy.cpp
Using Visual C++ 2012, without precompiled headers:
When I change a header file that is included in multiple files, the change is not taken into account when building.
If I rebuild all, the change is taken into account.
Reproduction case:
include.h
#ifndef INCLUDE_H_
#define INCLUDE_H_
class A {
public:
A(int i) : i_(i) { }
int i_;
};
class B {
public:
B(int i = 1) : a_(i) { }
A a_;
};
#endif INCLUDE_H_
dummy.cpp
#include "include.h"
main.cpp
#include <iostream>
#include "include.h"
int main(int, char**) {
B b;
std::cout << b.a_.i_ << std::endl;
return 0;
}
This outputs 1.
Now I change int i = 1 to int i = 2 in include.h; I build and run, it outputs 1!
I rebuild and run, it outputs 2.
The dummy.cpp file is necessary to reproduce the error. In real-life, this file is using include.h but not classes A and B (but this doesn't seem to change anything; declaring a class C with members A and B in dummy.cpp will still reproduce the problem). When removing the file dummy.cpp, or renaming it to zdummy.cpp (presumably it will be compiled after main.cpp), then the problem disappears.
I tried with include guards, with pragma once, with both of them, with none of them, the problem is reproduced in each case.
I cannot reproduce this problem with Code::Blocks/GCC; I didn't try with older versions of Visual Studio.
Am I missing something or is this really a bug in Visual Studio? If the latter, is there a known workaround? (Other than re-building at every step)
The header file must be part of the project. If it isn't the project will still build i.e. the compiler can find it, but Visual Studio won't track the date of the file.
I've been through such thing in the past.
Do you use precompiled headers? If you do please remove any project specific headers from the PCH. That is a lame mistake. Only place external, nonchanging headersin PCH, like C/C++ standard headers, Windows headers, Boost etc.
I have the following files
file1_moduleA.hpp
file1_moduleA.cpp
sharedFile.hpp
file1_moduleB.cpp
//sharedFile.hpp
extern CustomClass *doSomething(CustomClass *var1, const char *var2);
extern CustomClass *doSomethingElse(const char *var1);
template <class MYCLASS_A>
void myFunction(CustomClass *var1, const char* var2){
assert(somthing);
if (condition){
new (MYCLASS_A);
}
}
//file1_moduleA.cpp
#include "sharedFile.hpp"
// Contains the definitions of doSomething and doSomethingElse among others
//file1_moduleA.hpp
// Other declarations
//file1_moduleB.cpp
#include"sharedFile.hpp"
//...SNIPPETS OF CODE
void someFunction(CustomClass* var1){
doSomething(var1, "FOO");
}
//...
The following are in one Visual Studio Project, Project A:
file1_moduleA.hpp, file1_moduleA.cpp and sharedFile.hpp
The following are in another VS Project, Project B:
file1_moduleB.cpp, file1_moduleB.hpp
Project A compiles and links perfectly, whereas Project B compiles but gives an unresolved symbol for CustomClass *doSomething(CustomClass *var1, const char *var2) at someFunction in file1_moduleB.cpp
I have tried defining the function with and without extern; tried using a separate file for the template in file1_moduleA.hpp; tried inducing dependency between ProjectB and ProjectA in VS, but nothing seems to work. I am unsure why the definition is not being found during linking. ProjectA.lib however, is being created.
Any help in this regard would be appreciated.
if you are using visual studio, and these are different project, then make project B dependent upon project A.
Right click on the solution.
Go to project dependencies.
Choose Project B.
Click Project A (making project B dependent upon Project A)
rebuild.
Did you include shared file in project B?