Qt Link Issue with MyClass::metaobject VS2005 - c++

Just quickly before I start, I have searched SO and Google for a length of time trying to solve this and have been unsuccessful.
I am trying to compile my project, which used to use a certain library for providing GUI functionality based on Windows Forms. Now my company has started to move to Qt, and I decided I would start to convert my small application to support Qt also.
At first it would not compile at all, due to missing headers. Now that is sorted, I am stuck with my final .exe not being able to link due to the following errors.
Creating library Bin\VS_V8\Win32\Debug\Disp.lib and object Bin\VS_V8\Win32\Debug\Disp.exp
QtMainMenu.obj : error LNK2001: unresolved external symbol "public: virtual struct QMetaObject const * __thiscall QtMainMenu::metaObject(void)const " (?metaObject#QtMainMenu##UBEPBUQMetaObject##XZ)
QtMainMenu.obj : error LNK2001: unresolved external symbol "public: virtual void * __thiscall QtMainMenu::qt_metacast(char const *)" (?qt_metacast#QtMainMenu##UAEPAXPBD#Z)
QtMainMenu.obj : error LNK2001: unresolved external symbol "public: virtual int __thiscall QtMainMenu::qt_metacall(enum QMetaObject::Call,int,void * *)" (?qt_metacall#QtMainMenu##UAEHW4Call#QMetaObject##HPAPAX#Z)
Bin\VS_V8\Win32\Debug\Disp.exe : fatal error LNK1120: 3 unresolved externals
Our company has a small "Qt Test App" that was written to play around with, which is where I have based my import from. I can compile and link that fine. From what I have gathered, the following properties must be met with Qt files:
Make sure QTDir is included
Add to the UI Files the UIC Compiler
Add to the Resoruce Files the Resource Compiler
Add to the created Header Files the MOC compiler.
I noticed I was missing the MOC Build Tool commands, so I have added them to my UI File's header. However this didnt change the linking problem. I read that I should delete all built files and do a clean to solve it. This didnt work either.
I have checked, and Q_OBJECT is defined in the class.
I am using VS2005 with the Qt Addin. I did not start a new project for Qt however, I am just using the old Visual Studio Solution / VCProj.
Any ideas where to go next?

#Cameron Stubber you need moc object .. You need to modify Custom Build Step.
You can find Custom Build Step in header file (which has Q_OBJECT) Properties by right click. Then type this commands ;
Command Line = $(QTDIR)\bin\moc.exe -I"$(QTDIR)\include\QtCore" -I"$(QTDIR)\include\QtGui" -I"$(QTDIR)\include" -I"$(QTDIR)\mkspecs\$(QMAKESPEC)" finddialog.h -o debug\moc_finddialog.cpp
Description = MOC finddialog.h
Outputs = debug\moc_finddialog.cpp
Additional Dependencies = $(QTDIR)\bin\moc.exe;finddialog.h
But carefull by writing this types you need to change somethings here like $(QTDIR) it is my enviroment variables you need to write full form of where your QT located like D:\qt_5\
and also you need to be carefull finddialog you should write your .h and .cpp files name
And then you need to create a folder by right clicking solution explorer Add\New Filter .. Make folder name as Generated Files
And last step right click Generated Files add\existing item and you will see Debug folder in your solution Project and add moc_"projectName".cpp
Then re-build your solution. Problem will be solved.
Also you should add C/C++ /General/Additional Library Directories
$(QTDIR)\include
$(QTDIR)\include\QtGui
$(QTDIR)\include\QtCore
And Link/General/Additional Library Directories
$(QTDIR)\lib
Link/Input/Additional Dependencies
qtmaind.lib
QtCored4.lib
QtGuid4.lib
But dont forget to change $(QTDIR) to your enviroment variables or location of your qt folder. Like D:\qt_4.7.4

Related

Unresolved externals with google test

I have a project I am trying to add google-test unit testing to. It is structured like so:
VM (project)
some source files
BytecodePrograms.h
VMTest (project, made by add project -> google test -> link dynamically, test VM)
pch.h
test.cpp
I added my VM project as an include directory in VMTest properties -> c/c++ -> general -> additional include directories
contents of test.cpp are:
#include "pch.h"
#include "BytecodePrograms.h"
TEST(TestCaseName, TestName) {
EXPECT_EQ(8, VMFibonacciImp(6));
EXPECT_TRUE(true);
}
If I build, I get the following errors
Error LNK2019 unresolved external symbol "public: __thiscall WVM::WVM(void)" (??0WVM##QAE#XZ) referenced in function "int __cdecl VMFibonacciImp(int)" (?VMFibonacciImp##YAHH#Z) WVMTest C:\Users\WadeMcCall\source\repos\Virtual Machine Visual Scripting\WVMTest\test.obj 1
Error LNK2019 unresolved external symbol "public: __thiscall WVM::~WVM(void)" (??1WVM##QAE#XZ) referenced in function "int __cdecl VMFibonacciImp(int)" (?VMFibonacciImp##YAHH#Z) WVMTest C:\Users\WadeMcCall\source\repos\Virtual Machine Visual Scripting\WVMTest\test.obj 1
Error LNK2019 unresolved external symbol "public: int __thiscall WVM::interpret(class std::vector<int,class std::allocator<int> >)" (?interpret#WVM##QAEHV?$vector#HV?$allocator#H#std###std###Z) referenced in function "int __cdecl VMFibonacciImp(int)" (?VMFibonacciImp##YAHH#Z) WVMTest C:\Users\WadeMcCall\source\repos\Virtual Machine Visual Scripting\WVMTest\test.obj 1
However, my VM project defines my WVM class and uses it and can build and run and BytecodePrograms.h includes VM.h which has the declaration for this class.
I feel like this must just be a problem with the set up of my projects in Visual Studio somehow, but I have no idea. I have been googling for 2 days straight and have found other people with similar problems but their solution never seems to work for me.
Any ideas? Thanks.
I found a solution here: https://stackoverflow.com/a/19709712/8488701
Similar to what Steve suggested, except instead of creating a whole new project, I use a post-build event to build my project to a library and then link google test to that. The advantage of this over Steve's solution is that you don't have to modify your main project at all and you can still build a unit testing project on top of it.
This is a link error indicating that it found the .h file but couldn't find the actual implementation found in the .cpp. If you have a LIB project then visual studio may take the cpp code compiled into the LIB project and add it to your EXE project.
To incorporate the code into the test project, you have two options.
You can add the .cpp files in your VM Project to your Test project as well, but this is not usually done.
Instead, if your VM project is now an EXE I would recommend creating a new project called VMLib as a LIB project and then adding that project to both the test project and the VM EXE project.

Linker error while unit testing with Visual Studio C++

I want to unit test my C++ project with Visual Studio. After adding the folders from my project as include path to my test project, I get linker errors when trying to compile the tests:
Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol "public: __thiscall Piece::Piece(enum Color)" (??0Piece##QAE#W4Color###Z) referenced in function "public: __thiscall Bishop::Bishop(enum Color)" (??0Bishop##QAE#W4Color###Z) ChessPlusPlus-Tests D:\Documents\Projects\ChessPlusPlus\ChessPlusPlus-Tests\BishopTests.obj 1
Error LNK2019 unresolved external symbol "public: __thiscall Board::~Board(void)" (??1Board##QAE#XZ) referenced in function "public: void __thiscall ChessPlusPlusTests::BishopTests::ValidMovesTest(void)" (?ValidMovesTest#BishopTests#ChessPlusPlusTests##QAEXXZ) ChessPlusPlus-Tests D:\Documents\Projects\ChessPlusPlus\ChessPlusPlus-Tests\BishopTests.obj 1
Error LNK2019 unresolved external symbol "public: void __thiscall Board::placePieceAt(class Piece * const,struct Position)" (?placePieceAt#Board##QAEXQAVPiece##UPosition###Z) referenced in function "public: void __thiscall ChessPlusPlusTests::BishopTests::ValidMovesTest(void)" (?ValidMovesTest#BishopTests#ChessPlusPlusTests##QAEXXZ) ChessPlusPlus-Tests D:\Documents\Projects\ChessPlusPlus\ChessPlusPlus-Tests\BishopTests.obj 1
Error LNK2001 unresolved external symbol "public: virtual class std::vector<struct Position,class std::allocator<struct Position> > __thiscall Bishop::getMovesFor(struct Position,class Board &)" (?getMovesFor#Bishop##UAE?AV?$vector#UPosition##V?$allocator#UPosition###std###std##UPosition##AAVBoard###Z) ChessPlusPlus-Tests D:\Documents\Projects\ChessPlusPlus\ChessPlusPlus-Tests\BishopTests.obj 1
Error LNK2001 unresolved external symbol "public: virtual class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > __thiscall Bishop::toString(void)" (?toString#Bishop##UAE?AV?$basic_string#DU?$char_traits#D#std##V?$allocator#D#2##std##XZ) ChessPlusPlus-Tests D:\Documents\Projects\ChessPlusPlus\ChessPlusPlus-Tests\BishopTests.obj 1
Error LNK2001 unresolved external symbol "public: virtual class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > __thiscall Bishop::toShortString(void)" (?toShortString#Bishop##UAE?AV?$basic_string#DU?$char_traits#D#std##V?$allocator#D#2##std##XZ) ChessPlusPlus-Tests D:\Documents\Projects\ChessPlusPlus\ChessPlusPlus-Tests\BishopTests.obj 1
My test source code:
#include "stdafx.h"
#include "CppUnitTest.h"
#include "Bishop.h"
#include "Board.h"
#include "TestUtils.h"
using namespace Microsoft::VisualStudio::CppUnitTestFramework;
namespace ChessPlusPlusTests
{
TEST_CLASS(BishopTests)
{
public:
TEST_METHOD(ValidMovesTest)
{
// Arrange
Board board{};
Bishop *piece = new Bishop{ Color::WHITE };
Position pos{ 3,3 };
board.placePieceAt(piece, pos);
// Act
auto validPositions = piece->getMovesFor(pos, board);
// Assert
TestUtils::AssertPositions(validPositions, {
0,0,0,0,0,0,0,1,
1,0,0,0,0,0,1,0,
0,1,0,0,0,1,0,0,
0,0,1,0,1,0,0,0,
0,0,0,0,0,0,0,0,
0,0,1,0,1,0,0,0,
0,1,0,0,0,1,0,0,
1,0,0,0,0,0,1,0,
});
}
};
}
Without adding the include path's the test project doesn't compile, since the header file includes in the main project rely on the include paths.
The main project compiles just fine.
Can someone help me to understand whats going wrong?
Thanks!
I believe the chosen answer is not correct. Tests typically should be run in their environment; therefore, they should not access the implementation (.cpp)
When you create a separate Test Project on Visual Studio (VS 2017) you need to create a reference to the project you want to test (right-click test project -> Add -> Reference -> tick projects):
Add a reference
If you see some linker errors, right-click from the Unit test project: Project->Linker->Input->Additional Dependencies->Edit
then add the path to your .obj files.
You could try something like "$(SolutionDir)ConsoleApplication1\$(IntDir)*.obj" where ConsoleApplication1 is the target project name.
Path to .obj
Initially, I only wanted to put a comment on Cornelis' post, but I couldn't.
https://www.codeproject.com/Tips/1085171/How-To-Do-Unit-Testing-with-Cplusplus-in-Visual-St
I found there that you have to add your .h and .cpp files as existing files also to the test project. That is left out on the official documentation or I missed it.
Now it works!
I just ran into the same problem and solved it differently, following this piece of Microsoft documentation: https://learn.microsoft.com/nl-nl/visualstudio/test/unit-testing-existing-cpp-applications-with-test-explorer?view=vs-2015&redirectedfrom=MSDN#objectRef
This solution is a bit cleaner, I think, as you don't end up with all the header files from your projects under test also showing up in your test project.
Lines from the documentation in italics, bold lines are my additions:
If the code under test does not export the functions that you want to test, you can add the output .obj or .lib file to the dependencies of the test project.
Create a C++ test project.
On the File menu, choose New, Project, Visual C++, Test, C++ Unit Test Project.
Make sure to add the projects that you want to test as References. If you forgot, you can also add these references later, in the Solution Explorer window.
In Solution Explorer, on the shortcut menu of the test project, choose Properties. The project properties window opens.
Choose Configuration Properties, Linker, Input, Additional Dependencies.
Choose Edit, and add the names of the .obj or .lib files. Do not use the full path names.
For me, there were only .obj files. I found them in the Intermediates folder, of which there are multiple versions, one for each combination of Solution Platform (x86 or x64) and Solution Configuration (Debug or Release). If you have a lot of .obj (or .lib) files, I found it convenient to open a terminal and run ls (or dir) to get the filenames, edit out the .log, .txt and .pdb filenames that I didn't need, and copy paste the list of .obj filenames into Visual Studio. For convenient editing, note that you can click on the dropdown arrow on the right hand side of the Additional Dependencies entry field and click on edit.
Choose Configuration Properties, Linker, General, Additional Library Directories.
Choose Edit, and add the directory path of the .obj or .lib files. The path is typically within the build folder of the project under test.
For me, I only had .obj files. I found them in the Intermediates folder, of which there are multiple versions, one for each combination of Solution Platform (x86 or x64) and Solution Configuration (Debug or Release). A convenient macro for setting this path for all 4 combinations is this: $(SolutionDir)bin\$(PlatformTarget)\$(IntermediateOutputPath)Intermediates. You might have to take out the bin\ part, as I have also seen the output folders set up directly in the Solution Directory, instead of in a separate binary folder.
Choose Configuration Properties, VC++ Directories, Include Directories.
Choose Edit, and then add the header directory of the project under test.
For this directory, it's okay to point directly to folders that are part of the project under test. There is no need to copy the header files over to the test project. It's also okay if this directory contains more than just the headers. For example, my source folder contains both the .h files and the .cpp files.
After following these steps, I was able to include the header files in my test code by simply writing:
#include "SomeHeaderName.h"
So, without any need to specify the folders that the header files are in.
Make sure to clean and rebuild your entire solution. Then, your tests should be able to access the functionality of the projects that you are testing.

LNK2019 : unresolved external symbol, searched for in a non-existing *.obj file

Good morning,
I have just inherited an application from a collegue who has left, and I'm already in trouble: the last thing we have done is porting the solution from Visual Studio 2010 to 2013.
Now while building one of the projects in the solution, I get following error message:
1>usharedmemory.obj : error LNK2019: unresolved external symbol "public: __cdecl C_NamedSemaphore::C_NamedSemaphore(char const *,unsigned int)" (??0C_NamedSemaphore##QEAA#PEBDI#Z) referenced in function "public: __cdecl C_RecursiveNamedSemaphore::C_RecursiveNamedSemaphore(char const *,unsigned int)" (??0C_RecursiveNamedSemaphore##QEAA#PEBDI#Z)
This error seems to be caused within the file "Y:\Ucam5\ucm\x\rip_mlfdpf\usharedmemory.obj" (within the project's directory), but after having a quick look, it seems that this *.obj file does not even exist.
Hence the next question: what can I do in order to be sure that the *.obj file gets created? I have already verified that the "usharedmemory.cpp" file is present in the directory of the main project (the corresponding *.h files is located in the "External Dependencies" chapter, which makes me believe that the *.obj file will be created during the build of the main project.
You see my problem: my project refers to a file which the project needs to create, but as the project does not create the file, he obviously can't refer to it, you see the circle I'm running in :-)
(for your information, I have no idea on how to generate an "*.obj" file)
Can anybody help me?
Thanks
Object files (*.obj) are created directly from source files (*.cpp) by the compiler at compilation time, for each source file in your project.
The error you are receiving is not caused by usharedmemory.obj not existing; it should be created in the Debug or Release folders.
The error you are getting is because usharedmemory.cpp uses the C_NamedSemaphore(char const *,unsigned int)-constructor of C_NamedSemaphore and the definition of the constructor can not be found in any of the source files. This constructor is used in the C_RecursiveNamedSemaphore(char const *,unsigned int)-constructor defined in usharedmemory.cpp. This is what the error message reads.
To solve this, you need to find out where the constructor of C_NamedSemaphore is defined (which source file) and ensure that this source file is included in your project. Or, if it is in a library file (static or dynamic), verify that this library file is included as an Additional Dependency (under project Properties -> Linker -> Input -> Additional Dependencies; ensure you set this for all builds, not just the currently active one).
Good morning,
I have finally solved my issue. As a good citizen, I will describe how I have done it :-), but as a less good programmer, I need to admit that I don't understand how my actions solve the problem ;-(
I have done a file comparison of both *.vcxproj Visual Project files (the old one from VC2010 and the new VC2013 one). In that way I have seen that the "umultiproc.cpp" entry was missing in the VC2013 one:
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
...
<ItemGroup>
...
<ClCompile Include="..\..\mp\umultiproc.cpp" /> <!-- missing -->
Summary: In the error message, there was an unresolved symbol (C_Semaphore constructor), which was defined in *.cpp/*.h source/header file. In order to solve the error, I have added a reference to the *.cpp source file into the VC2013 project file.

Google Protocol buffer c++ link error when trying to use it in project

I am trying to get protocol buffer to work but linking problems occurs.
All the errors looks something along like this
error LNK2019: unresolved external symbol "public: bool __cdecl google::protobuf::MessageLite::ParseFromArray(void const *,int)" (?ParseFromArray#MessageLite#protobuf#google##QEAA_NPEBXH#Z) referenced in function "void __cdecl ReceiveRequest(bool *)" (?ReceiveRequest##YAXPEA_N#Z)
I am using visual studio pro 2013 and this is what I have done:
I compiled the protocol buffer and added the libprotobuf.lib to the project(Add->Existing Item->libprotobuf.lib)
I've added the header files in C/C++ -> General -> "Additional Include Directories"
I have tried to add the library all the different ways I know but I still get these linking errors...
Any idea what I might have done wrong?
// Eric
You need to include the generated protocol buffer .cc (and maybe the .h) file (ie the file with the specific getters and setters for your specific proto) in your VS project (ie there has to be a little icon for them in the solution explorer) or else visual studio won't generate the code for it and thus there's nothing to link to.
Make sure you have the correct libraries for your architecture (e.g. x86 / x64).
That has caught me out a few times.

How to add cpp files to Visual Studio 2008?

I'm trying to add Beecrypt library to my project. First i have added header files but after attempting to create an object i'm receiving the following errors:
error LNK2019: unresolved external symbol "__declspec(dllimport) public: virtual __thiscall beecrypt::security::SecureRandom::~SecureRandom(void)" (__imp_??1SecureRandom#security#beecrypt##UAE#XZ) referenced in function _wmain
As far as i understand it is due to the absence of cpp files. Ok. Then i'm trying to add cpp files but whatever folder i put them i still receive the same error. For example SecureRandom.h is situated:
beecrypt/c++/security/SecureRandom.h
Where should i put SecureRandom.cpp to get rid of that error? I've already tried all levels of folders. Or maybe that error is caused by something else? Thanks a lot in advance
Simplest way is to Just drag and drop them to your project in the solutions explorer.
Or
Follow the steps given in the link below on MSDN website:
Adding a Source File.