One or More Multiply Defined Symbols Found

One or more multiply defined symbols found

Put the definition (body) in a cpp file and leave only the declaration in a h file. Include guards operate only within one translation unit (aka source file), not across all your program.

The One Definition Rule of the C++ standard states that there shall appear exactly one definition of each non-inline function that is used in the program. So, another alternative would be to make your function inline.

Error: one or more multiply defined symbols found

I am not sure is main is related to the problem

Oh, yes, it is! :-)

By including game.cpp into main.cpp, you define all the things in game.cpp twice, once in the main object file and once in the game object file. Object files aren't necessary for an implementation but they're common enough to use as an explanation. In any case, the fact your error message mentions game.obj indicates your environment does use them.

Including a file really just substitutes the #include line with the contents of the file, explaining why both object files end up having the same definitions.

Then, when you link the two object files together, voila, symbols defined twice.

You should generally never include cpp files into other cpp files since they tend to define things that you would rather not have multiple copies of. Instead you should include header files, which tend to just declare things.

This is an important distinction that I explain to students as follows. A declaration is just declaring that something exists, without actually creating it. You can do that as many times as you want. A definition, on the other hand, brings it into existence, and you really only want to do that once.

The one-definition rule is what you should investigate if you want to understand this more than my greatly simplified explanation provides for.

LNK1169 one or more multiply defined symbols found. I know this could be considered a duplicate but I could not find anything that solved my problem

When exporting global variables, you want them to be defined in your c++ file so that it gets compiled only once by the compiler.

Currently, including it from the .h file adds it to all of your .obj files (built by the compiler) and the linker does not like the same variable existing at multiple places when it tries to build your .exe or library.

What you need to do is to declare the variable as "extern" in the header file, and add its declaration (identical) to an appropriate .cpp file.

in the header :

extern int number_of_employee;

In the .cpp

int number_of_employee;

Additionally, if you want to use a global variable within a .cpp file, but you don't want it to be modifiable by any external files that declare

extern int your_variable_name;

You ought to define it as "static", which means it will not be seen by the linker, and will be "private" to the .obj it's defined in.

Edit (like so):

static int your_variable_name;

Edit (as per @dxiv's comment):

Since c++17, a possibly preferred way of doing this (since it results in less bloat) is to declare your variable as inline - which tells the linker that it is allowed to have multiple declarations and, in case of variables, that all declarations should be merged as a single binary bit of data in the final binary.

inline int number_of_employee;

To make sure you have c++17 or later enabled with msvc++, you can check that you have the /std:c++17 or /std:c++latest flag in your project properties, in visual studio under

project -> properties -> Configuration properties -> General -> C++ Language Standard.

For completion sake, with the GNU or GNU-inspired compilers, you'd need the flag -std=c++17.

Have a nice evening,

Error LNK1169 one or more multiply defined symbols found

Yes, if you have a (non inline) global variable defined in the header, and the header is included into several .cpp files, you will have linker errors due to ODR violations.

A most common fix in legacy C++ is to move the definition into the .cpp file and leave the .h file with a declaration:

In .h:

extern int __invReasonCounts[7];

In .cpp:

int __invReasonCounts[7] = {0}; // compile-time initialization, safe

Also, keep in mind that symbols beginning with __ (two undescores) are reserved for implementation and not to be used in program code.

LNK1169 one or more multiply defined symbols found And LNK2005

When you build your project, each .cpp file gets compiled separately into different object files. The once in #pragma once only applies to the compilation of a single .cpp file, not for the project as a whole. Thus if a .cpp file includes header A and header B, and header B also includes header A, then the second include of header A will be skipped.

However, if you have another .cpp file that includes A, A will be included in that object file again -- because #pragma once only works when compiling a single .cpp file.

An #include statement literally takes the content of the included file and "pastes" it into the file that included it. You can try this by looking at the output of the C preprocessor tool (cpp in the gcc toolchain). If you are using the gcc toolchain, you can try something like this to see the file after its includes have been applied:

cpp file.cpp -o file_with_includes.cpp

If you have a function in your header, like Assert in your example, the function gets replicated into each .cpp file you include it in.

If you have A.cpp and B.cpp, that both include your Constants.h file, each object file (.o or .obj depending on your environment) will include a copy of your Assert function. When the linker combines the object files to create a binary, both object files will declare that they provide the definition for Assert, and the linker will complain, because it doesn't know which one to use.

The solution here is either to inline your Assert function, like this:

inline void Assert(bool val, string s)
{
if (!val)
{
cout << "Assertion Failed!!: " << s << endl;
exit(-1);
}
}

or to provide its body in its own .cpp file, leaving only the function prototype in the header.

Constants.h:

void Assert(bool val, string s);

Constants.cpp:

void Assert(bool val, string s)
{
if (!val)
{
cout << "Assertion Failed!!: " << s << endl;
exit(-1);
}
}

Mind you, the Standard Library also offers assert(), which works nicely too. (see https://en.cppreference.com/w/cpp/error/assert).

#include <cassert>
...
assert(is_my_condition_true());
assert(my_variable > 23);
// etc..

Just keep in mind that the assert declared in cassert only works when compiling for Debug, and gets compiled out when building for Release (to speed up execution), so don't put any code in assert that has side effects.

#include <cassert>
...
// Don't call functions with side effects.
// Thus function decreases a "count" and returns the new value
// In Release builds, this line will disappear and the decrement
// won't occur.
assert(myclass.decrement_count() > 0);

fatal error LNK1169: one or more multiply defined symbols found in game programming

The two int variables are defined in the header file. This means that every source file which includes the header will contain their definition (header inclusion is purely textual). The of course leads to multiple definition errors.

You have several options to fix this.

  1. Make the variables static (static int WIDTH = 1024;). They will still exist in each source file, but their definitions will not be visible outside of the source file.

  2. Turn their definitions into declarations by using extern (extern int WIDTH;) and put the definition into one source file: int WIDTH = 1024;.

  3. Probably the best option: make the variables const (const int WIDTH = 1024;). This makes them static implicitly, and also allows them to be used as compile-time constants, allowing the compiler to use their value directly instead of issuing code to read it from the variable etc.

How can I resolve this one or more multiply defined symbol found error?

How can I fix this?

You could solve this by adding/using the keyword inline for the specialization so the specialization would look like:

   //note the keyword inline in the below specialization
template <> inline
double my_template_function<double>(double parameter)
{
std::cout << "function specialization on double";
std::cout << parameter;
return parameter;
}

This works as can be seen here.

Second way to solve this would be to move your specialization into the source file instead of the header. So your template_specialization_conflict_test.cpp would look like:
template_specialization_conflict_test.cpp

#include "template_specialization_conflict_test.hpp"

namespace utils
{
// Template Specialization
// A function specialized for double data type
template <>
double my_template_function<double>(double parameter)
{
std::cout << "function specialization on double";
std::cout << parameter;
return parameter;
}
}

The program works as can be seen here and here(with gcc and clang).

one or more multiply defined symbols found with include

Now that the question has been reopened, I'll post this as an answer instead of a comment.

Basically, the issue is that, when compiling, each time the compiler sees WindowData* windowData; (for example), it will create a new variable and know to allocate space for windowData. Later, the linker is trying to put this all together, and realizes there's more than one windowData variable, so you get the "already defined" error you are getting.

To solve it, you only want to define the variables once, most likely in your "Settings.cpp" file. Then, for the header file, you would mark each declaration with extern, so that the compiler will know that variable exists somewhere, but won't try to allocate anything to it.

So, something like this:

Settings.h

#pragma once
#include "WindowData.h"
#include "Time.h"
#include "Camera.h"
#include "ShaderManager.h"
#include "InputManager.h"

extern WindowData* windowData;
extern Time* timeControl;
extern Camera* cam1;
extern InputManager* inputManager;
extern ShaderManager* shaderManager;

Settings.cpp

#include "Settings.h"

WindowData* windowData;
Time* timeControl;
Camera* cam1;
InputManager* inputManager;
ShaderManager* shaderManager;

Problems with multiply defined symbols found (LNK 1169)

In the header:

struct avl_node
{
int data;
avl_node* left;
avl_node* right;
};
extern avl_node* root;

In exactly one source file:

#include "ThatHeader.h"
avl_node* root;

Currently, you put the definition of root into the header. Which means that every source file that includes this header ends up containing that definition. And when those files are linked together, the linker discovers multiple definitions of the same name, and complains.

The solution is to provide only a declaration in the header file (that's what extern keyword does), and a definition in only one source file.

See also: One Definition Rule



Related Topics



Leave a reply



Submit