Multiple definitions when using #ifdef - c++

I am having a problem when compiling: Multiple definitions of "myFunction()"
I will greatly simplify the problem here. Basically, I have 3 files: "main", "header", and "myLibrary".
main.cpp
#include "header.hpp"
int main() { }
header.hpp
#ifndef HEADER_HPP
#define HEADER_HPP
#include "myLibrary.hpp"
// ...
#endif
header.cpp
#include "header.hpp"
// ...
myLibrary.hpp
#ifndef LIB_HPP
#define LIB_HPP
#if defined(__unix__)
#include <dlfcn.h>
std::string myFunction() { return std::string(); }
#endif
#endif
myLibrary.cpp
#include "myLibrary.hpp"
//...
So, why does the compiler say that I have Multiple definitions of "myFunction()"?
One clue I found: When I take header.cpp and erase the line that says #include "header.hpp", the program compiles without complaining. On the other hand, if I erase myFunction (from myLibrary.hpp) instead, the program also compiles without complains

You are defining the body of the function inside the header file. So every translation unit that you include that header in (in this case, main.cpp and header.cpp) will end up with its own copy of that function body. And when you try to link those multiple units together, you get the "duplicate definition" error.
The function needs to be declared in the hpp file, and defined in the cpp file:
myLibrary.hpp
#ifndef LIB_HPP
#define LIB_HPP
#if defined(__unix__)
#include <dlfcn.h>
#include <string>
std::string myFunction();
#endif
#endif
myLibrary.cpp
#include "myLibrary.hpp"
#if defined(__unix__)
std::string myFunction()
{
return std::string();
}
#endif
//...

Include guards only prevent the same header from being included twice within the same translation unit, which in practice is usually a single .cpp file. For example, it prevents errors when doing this:
#include "header.h"
#include "header.h"
int main()
{
}
But, more generally, it means that it doesn't matter if you've include a header that has already been included as a dependency of another header.
However, if you have two .cpp files include the same header, and that header contains the definition of a function (such as your myLibrary.hpp) then each .cpp file will have its own definition (the include guard won't help because the header is being included in two separate translation units / .cpp files).
The simplest thing to do is to declare the function in the header, which tells every file that includes your header that the function exists somewhere, and then define it in the .cpp file so that it is only defined once.

You should to define functions in the .cpp files, not in the header files. You declare them in the header files. What you're doing is defining it in the header file, so when it gets included into multiple files, the function is getting duplicated. Cross-file duplicate symbols will throw an error, unless they're static.
myLibrary.cpp:
#include "myLibrary.hpp"
#ifdef(__unix__)
std::string myFunction() { return std::string(); }
#endif
myLibrary.hpp:
#ifndef LIB_HPP
#define LIB_HPP
#if defined(__unix__)
#include <dlfcn.h>
#include <string>
std::string myFunction();
#endif
#endif

Related

If you include something in the .h file Do you have to include the same thing again?

So I am just wondering if you #include something in a for example header.h file:
For example this is called header.h:
#include <vector>
#include <iostream>
#include <somethingElse>
So if for example I make a file called something.cpp Do I need to put all those include statements again?
#include "header.h"
// If I include #header.h in this file. Do the #include carry over to this file. Or do they not
I am wondering because whenever I include <vector> something in my .h file the #include statements that I used previously in the .h file always turn grey which means they are not used. Is it because I used it in the .h file? Its not a problem or anything I am just curious.
You don't need to include those headers again because your compiler can find those headers. You can also try to read and understand the makefile (or CMakeList) which will help.
Try always to avoid "Multiple file inclusion" via using inclusion guard or #pragma once in order to prevent the multiple file inclusion.
To include file means that the content of the file will be added to the very place you wrote include.
Here's an example:
// header.h
const int vlaue = 10;
const int value2 = 0;
// main.cpp
#include "header.h"
#include "header.h"
Above the content of "header.h" is added twice to main.cpp.
Do you know what is the result? It's a compile-time error complaining of redefinition of value and value2.
In the above example I think green programmers don't get trapped by it but it is just an explanation, So what I talk about is when a huge program where many header files and many source files and some files include others then it'll be so difficult to track the right file inclusion.
The workaround that is to use inclusion guards or pragma once eg:
Let's modify our header.h to look like:
// header.h
#ifndef MY_HEADER_H
#define MY_HEADER_H
const int vlaue = 10;
const int value2 = 0;
#endif
Now in main.cpp:
#include "header.h"
#include "header.h"
#include "header.h"
The code above works fine and no duplicate of header content is added to main.cpp. Do you know why? It's the magic of Macro there. So at first time the pre-processor checks whether a macro has been already defined with the name MY_HEADER_H or not and for sure for the first time it is not defined so the content is added. The second and so on the condition fails because the macro is already defined thus the content of header.h will not be added to where it is called.
The draw back of inclusion guard is if you have a macro with same name as the inclusion guard thus it is already defined so the content will never be added (empty content). Thus you get a compile-time error:
value, `value2` undeclared identifiers.
The second solution is using pragma eg:
Let's modify our header.h file:
// header.h
#pragma once
const int vlaue = 10;
const int value2 = 0;
// main.cpp
#include "header.h"
#include "header.h"
The code above works correctly so no multiple inclusion of header.h That is because of the magic of pragma once: which is a non-standard but widely supported pre-processor directive designed to cause the current source file to be included only once in a single compilation. Thus, #pragma once serves the same purpose as include guards, but with several advantages, including: less code, avoidance of name clashes, and sometimes improvement in compilation speed.
Finally you should include header wherever their content is used eg:
// Shape.h
class Shape{
// some code here
};
// Cube.h
#include "Shape.h"
class Cube : public Shape{
// some code here
};
// Cuboid.h
// #include "Shape.h"
#include "Cube.h" // So here the Shape.h is added to Cube.h and Cube.h is added here.
class Cuboid : public Cube{
// some code here
};
As you can see above the content of Shape.h is added to Cuboid.h indirectly because it is added to Cube.h and cuboid.h includes Cube.h so it is added to it. So without inclusion guards or pragma once if you include the two headers in one source file you get duplicate content there.

Why linker is giving error for global variable in header file

I have declared a global variable in header.h and included that header in source.cpp and main.cpp but linker is giving error
Source.obj : error LNK2005: "int globalVariable" (?globalVariable##3HA) already defined in Main.obj
GlobalVariableAndLinkageIssue.exe fatal error LNK1169: one or more multiply defined symbols found
header.h
int globalVariable;
source.cpp
#include "header.h"
main.cpp
#include"header.h"
void main() {}
Move the declaration to a .cpp file. You can use a declaration in a header file by using:
extern int globalVariable; // declaration in header - can have as many as you need
But the .cpp file should have the definition:
int globalVariable; // definition in .cpp - only need one across all your files
C and C++ use textual pre-processor to include headers, this is basically a text insertion, not a smart module system as in some languages. By including it as you were, you are creating multiple definitions, one per .cpp file.
As a matter of good practice, you need to get used to using include guards to protect against multiple nested includes (though it would not solve your current issue). If using Visual C++, you can use #pragma once or to use a portable solution wrap your header code in:
#ifndef _INCLUDE_FOO_H_
#endif
To create a global variable, you should do the following. Note that in the header, we mark the variable as extern, and we actually create the object in a cpp file.
header.h
extern int globalVariable;
header.cpp
#include "header.h"
int globalVariable;
main.cpp
#include "header.h"
int main() {}
Put global variable in some .c or .cpp file, so that it can be defined only once and refer in header file using extern
for example,
header.h
extern int globalVariable;
header.cpp
int globalVariable = 0;
source.cpp
#include "header.h"
main.cpp
#include"header.h"
int main() {
return 0;
}
Because BOTH sources #include your header, and thus it is DEFINED twice.
In such situation,it is common to use some #define as follows:
//header.h
#ifdef DEFINE_VARS
#define DEFINE_OR_DECLARE
#else
#define DEFINE_OR_DECLARE extern
#endif
DEFINE_OR_DECLARE int globalVariable;
//main.cpp
#define DEFINE_VARS
#include "header.h"
...
//header.cpp
#include "header.h"
...

Redefinition of function

I have one file example1.cpp with the main function. This file must have #include mylib.h and #include lib.h. File mylib.h also has #include lib.h. When I try to compile this program, the error redefinition xyz function ocurs.
example1.cpp
#include mylib.h
#include lib.h
int main(){
//code
}
mylib.h
#include lib.h
//rest code
You need to put include guards in your header file to prevent it from getting included multiple times during compilation.
#ifndef LIB_H
#define LIB_H
// Actual header file code
#endif
You have to wrap the .h files in #defines to avoid the redifinitions. For example:
#if !defined(_MY_LIB_H_)
#define _MY_LIB_H_
// Add your function definitions here...
#endif // _MY_LIB_H_
You can now include it anywhere and the function definition will be read once. Also note that you can use #ifndef depending on the compiler. VC++ for example, allows "#pragma once" if it's version 10 or higher:
#if _MSC_VER > 1000
#pragma once
#endif
In this case, you don't need to use the #defines explained above.

C++: Header issues

I just can't win with headers it seems.
I have a class Log of which has a header Log.h that defines the class Log, and then the Log.cpp implements the methods of Log. I need it available in Main.cpp, so I include Log.h into Main.cpp and I receive the notorious "already defined" errors.
If I take out the header from Main.cpp, I can't use the class.
If I take out the header from Log.cpp, then Log is (obviously) not defined.
I can't win here! What do I do?
EDIT YES, of course I have include guards.
#ifndef LOG_H_
#define LOG_H_
namespace vexal {
#define CCOL_RESET "^[[0m"
#define CCOL_RED "^[[31m"
class Log {
public:
Log();
virtual ~Log();
static void genInstance();
private:
static Log* _inst;
};
}
#endif /* LOG_H_ */
Then the includes are merely #include "Log.h" in both Log.cpp and Main.cpp.
Have you included include guards?
Log.h
#ifndef LOG_H
#define LOG_H
// your code here
#endif
Sounds like you might not have include guards? Try adding to the top of your header file:
#ifndef LOG_HEADER_FILE
#define LOG_HEADER_FILE
And then at the bottom of your header file:
#endif
The issue ended up being the order of which the includes were included. Some includes have to be included before others to avoid redefinition issues.
This is rather vague, but most likely you need some include guards in your header. If you're using MSVC, a #pragma once up the top should do. If not, something standard like:
#ifndef LOG_H_
#define LOG_H_
///Rest of header file
#endif

Visual Studio C++ Headers

I need to create structure like this:
// file main.h:
#pragma once
#ifndef _MAIN_H
#define _MAIN_H
#include <iostream>
#include "first.h"
#include "second.h"
#endif
// -----------------
// file first.h:
#pragma once
#ifndef _FIRST_H
#define _FIRST_H
#include "main.h" // because of using SomeFunction() in first.cpp
int SomeVar; // used in first.cpp
#endif
// -----------------
// file second.h:
#pragma once
#ifndef _SECOND_H
#define _SECOND_H
#include "main.h" // because of using SomeVar in second.cpp
int SomeFunction(); // implemented in second.cpp
#endif
// -----------------
By logic, if main.h will be compiled first, then each of this headers will be included only once and all variables/functions will be defined normally.
For example, this configuration compiled normally in IAR C++ Compiler, if set up in options "preinclude file" (not precompiled) to main.h.
But, in Visual Studio 2010 same structure causes linker errors like:
1>second.obj : error LNK2005: "int SomeVar" (?SomeVar##3HA) already defined in first.obj
1>second.obj : error LNK2005: "int SomeFunction" (?SomeFunction##3HA) already defined in first.obj
I think because of including files in alphabetic order. Apparently pragma- and define-guards are ignored by linker.
Errors can be fixed by additional header and external variables definitions, but this is hard and wrong way.
Question is: What should i do?
int SomeVar; // used in first.cpp
Variables should never be defined in headers. They should be declared with extern:
extern int SomeVar; // used in first.cpp
Then you can actually define them in "first.cpp" with int SomeVar;.
Also, "first.h" does not need to include "main.h". Headers should only include files if the definitions in that header absolutely need the contents of those files. The definitions in "first.h" do not need anything in "main.h". Therefore, it should not include it.
If "first.cpp" needs to include something from "second.h", then it is the responsibility of "first.cpp" to include it.
In the header file use extern keyword as:
//first.h
extern int SomeVar; //extern tells the compiler that definition is elsewhere
Then in .cpp file define it and use it:
//first.cpp
int SomeVar; //definition is here
As for SomeFunction, have you defined it header file itself? Re-check it. :-)