I have a project with multiple header files and .cpp files.
All of the header files have include guards.
There is a file called Constants.h where I define some constants. Some of these with defines, some as constant variables.
There are more header-.cpp-file pairs with code in them. One of these does contain a class, the others don't.
When I include my files into my main file (an arduino sketch), I get a lot of linker errors, claiming there are multiple definitions of some variables.
I read that this mainly occurs when you include .c or .cpp files, which I don't do. All the .cpp files only include their appropriate header files.
I did manage to find multiple solution proposals:
1) inline:
With functions, inline can be used to get rid of this problem. However, this is not possible with variables.
2) anonymous namespace:
This is one of the solutions I used. I put anonymous namespaces around all the problematic definitions I had. It did work, however I do not understand why this works. Could anyone help me understand it?
3) moving definitions into .cpp files:
This is another approach I used sometimes, but it wasn't always possible since I needed some of my definitions in other code, not belonging to this header file or its code (which I do admit is bad design).
Could anyone explain to me where exactly the problem lies and why these approaches work?
Some of these with defines, some as constant variables.
In C const does not imply the same thing as it does in C++. If you have this:
const int foo = 3;
In a header, then any C++ translation unit that includes the header will have a static variable named foo (the const at namespace scope implies internal linkage). Moreover, foo can even be considered a constant expression by many C++ constructs.
Such is not the case in C. There foo is an object at file scope with external linkage. So you will have multiple definitions from C translation units.
A quick fix would be to alter the definitions into something like this:
static const int foo = 3;
This is redundant in C++ but required in C.
In addition to Story Teller's excellent explanation, to define global variables, use the following:
// module.h
#include "glo.h"
// glo.h
#ifndef EXTERN
# define EXTERN extern
#endif
EXTERN int myvar;
// main.c
#define EXTERN
#include "glo.h"
In main.c all variables will be declared (i.e. space is allocated for them), in all other c files that include glo.h, all variables will be known.
You shouldn't declare any object in header files, this should be moved to c\c++ files.
In header you may:
declare types such as: classes, structs, typedefs etc.
put forward declarations of (not classes) functions
put inline (or in classes) functions (+ body)
you may add extern declaration.
you may put your macros.
a static declaration may declare things multiple times, therefore it is not recommended.
Related
This question already has answers here:
Multiple definition of a function error, even when using #if guard clauses
(5 answers)
Closed 6 years ago.
I initialised some arrays in a file called Fares.cpp in my project. When I try using #include "Fares.cpp" in my main.cpp file (where the main code for the project is) in Dev-C++, the compiler gives an error saying “multiple definition”. I don't know what to do, please help.
I don’t know much about macros, extern etc.
Try including "Fares.h" instead of "Fares.cpp". #include is usually used to include header files which usually contain variable declarations and function prototypes. Check this link for more info: http://www.learncpp.com/cpp-tutorial/19-header-files/
Traditionally, .c and .cpp files are related to single compile unit (module, etc.), processed by compiler separately. Include meant to add files called "header files" or "include files" to the file scope, making declarations, inline functions definitions and type definitions in them being available to syntax analyzer of compiler.
Declarations include:
Function declaration
Template declaration
Explicit template instantiation
Explicit template specialization
Namespace definition
Linkage specification
Attribute declaration (attr ;) (since C++11)
Empty declaration (;) (since C++11)
To avoid multiple definition of same classes or functions, header files must use #ifndef blocks as "brackets"
// beginning of file.h
#ifndef SOME_UNIQUE_ID
#define SOME_UNIQUE_ID
// declarations , etc.
#endif
// end of file .h
There is nothing that prevents use of different suffixes, it's matter of how build process is organized. There is common agreement to name C files .c, C++ - .cpp, standard C++ headers wouldn't have suffix at all, while all other headers may have .h or .hpp. Include files that contain only inline functions sometimes are given .inc or .inl suffix instead of .h, but this isn't regulated in any way as far as I know
You can have only one definition per same scope with same ID. More of even while you may have several file scopes, for each .cpp a non-static declaration would generate duplicate IDs that would cause link-time error. You really should avoid using .cpp as include file, because in most build environments compiler would attempt to link it multiple times - for each use in #include and as separate module as well.
In your case you should put declarations of your arrays into .h file in form like this:
// fares.h
#ifndef FARES_H_
#define FARES_H_ // this will not allow declaration to be repeated
extern int gYourGlobalArray[100];
#endif
Word extern will tell the compiler that the symbol is defined elsewhere and would be found on link stage, the object should be static or thread storage duration, which in our case true as we declare global variable, and gets external linkage. Fares.cpp will have "implementation" that must contain symbols that will not be repeated.
// Fares.cpp
#include "fares.h" // necessary only if you require something declared there
// keep in mind that some file systems are case sensitive, some aren't and
// will not distinguish between Fares.h and fares.h
int gYourGlobalArray[100] = {};
That's actually defines thread duration storage for your array in file scope and allows it to be linked externally. Across entire project its identification should be unique (C++ compiler mangles names of some objects, e.g. functions, but in general you should avoid reusing IDs). If for some wild reasons ID in file scope repeats in different files but should not be linked externally, such storage should be declared static, that would disallow external linkage.
Declaring a static member of class usually either require similar definition in .cpp file (without keyword static) or requires initialization within class body, provided compiler supports that.
Next you only should add fares.cpp to your project\makefile\whatever you are using as compiling environment. fares.h goes into #include statements into .cpp or .h files that require it. #include statement technically just adds text of mentioned file to file wrote it in, exactly in that position.
I have what seems a relatively simple question, but one that keeps defying my efforts to understand it.
I apologise if it is a simple question, but like many simple questions, I can't seem to find a solid explanation anywhere.
With the below code:
/*foo.c*/
#include "bar.h"
int main() {
return(my_function(1,2));
}
/*bar.h*/
int my_function(int,int);
/*bar.c*/
#include "bar.h" /*is this necessary!?*/
int my_function(int x, int y) {
return(x+y);
}
Simply, is the second inclusion necessary? I don't understand why I keep seeing headers included in both source files. Surely if the function is declared in "foo.c" by including "bar.h," it does not need to be declared a second time in another linked source file (especially the one which actually defines it)??? A friend tried to explain to me that it didn't really matter for functions, but it did for structs, something which still eludes me! Help!
Is it simply for clarity, so that programmers can see which functions are being used externally?
I just don't get it!
Thanks!
In this particular case, it's unnecessary for the reason you described. It might be useful in situations where you have a more complex set of functions that might all depend on each other. If you include the header at the top of the .cpp file, you have effectively forward-declared every single function and so you don't have to worry about making sure your function definitions are in a certain order.
I also find that it clearly shows that these function definitions correspond to those declarations. This makes it easier for the reader to find how translation units depend on each other. Of course, the names of the files might be sufficient, but some more complex projects do not have one-to-one relationship between .cpp files and .h files. Sometimes headers are broken up into multiple parts, or many implementation files will have their external functions declared in a single header (common for large modules).
Really, all inclusions are unnecessary. You can always, after all, just duplicate the declarations (or definitions, in the case of classes) across all of the files that require them. We use the preprocessor to simplify this task and reduce the amount of redundant code. It's easier to stick to a pattern of always including the corresponding header because it will always work, rather than have to check each file every time you edit them and determine if the inclusion is necessary or not.
The way the C language (and C++) is designed is that the compiler processes each .c file in isolation.
You typically launch your compiler (cl.exe or gcc, for example) for one of your c files, and this produces one object file (.o or .obj).
Once all your object files have been generated, you run the linker, passing it all the object files, and it will tie them together into an executable.
That's why every .c file needs to include the headers it depends on. When the compiler is processing it, it knows nothing about which other .c files you may have. All it knows is the contents of the .c file you point it to, as well as the headers it includes.
In your simplified example inclusion of "bar.h" in "bar.c" is not necessary. But in real world in most cases it would be. If you have a class declaration in "bar.h", and "bar.c" has functions of this class, the inclusion is needed. If you have any other declaration which is used in "bar.c" - being it a constant, enum, etc. - again include is needed. Because in real world it is nearly always needed, the easy rule is - include the header file in the corresponding source file always.
If the header only declares global functions, and the source file only implements them (without calling any of them) then it's not strictly necessary. But that's not usually the case; in a large program, you rarely want global functions.
If the header defines a class, then you'll need to include it in the source file in order to define member functions:
void Thing::function(int x) {
//^^^^^^^ needs class definition
}
If the header declares functions in a namespace, then it's a good idea to put the definitions outside the namespace:
void ns::function(int x) {
//^^^^ needs previous declaration
}
This will give a nice compile-time error if the parameter types don't match a previous declaration - for which you'd need to include the header. Defining the function inside its namespace
namespace ns {
void function(int x) {
// ...
}
}
will silently declare a new overload if you get the parameter types wrong.
Simple rule is this(Considering foo is a member function of some class):-
So, if some header file is declaring a function say:=
//foo.h
void foo (int x);
Compiler would need to see this declaration anywhere you have defined this function ( to make sure your definition is in line with declaration) and you are calling this function ( to make sure you have called the function with correct number and type of arguments).
That means you have to include foo.h everywhere you are making call to that function and where you are providing definition for that function.
Also if foo is a global function ( not inside any namespace ) then there is no need to include that foo.h in implementation file.
So I have made a complex project and now I have too many include files causing me headaches. How can I best manage these classes? Some classes need to use other classes. I also have a .h file containing a bunch of arrays of int. These stay the same through the application but I get the problem when the compiler complains that I am redefining the array.
Should I make a class library? Namespace? DLL? What is the best practice and where can I find out how to do the right one?
Use include guards in all your headers.
file.h
#ifndef FILE_H_INCLUDED
#define FILE_H_INCLUDED
void foo();
#endif
Avoid global variables when possible. If you must use them, declare global variables using extern and place the definition in a .cpp file instead.
file.h
extern int var[20];
file.cpp
int var[20];
When possible, use forward declarations. You can use forward declarations whenever you use only a reference or a pointer to a class and don't dereference that pointer.
useful.h
class Useful {};
other.h
// Forward-declare instead of #include
class Useful;
class Other
{
Useful* helper;
};
I don't think there really is a best practice, it depends on the situation. Something I might recommend is to group like objects into a namespace then put all of the definitions in a single .h file. If the implementations are short, put them all in a single cpp file. Here at my work we have a database access layer like this. There are roughly a couple dozen objects that are populated by stored procs. The code is still a major pain in the ass but it's better than having two dozen .h and cpp files that are all less than 500 lines. If you do this comments to compartmentalize object definitions become really important. You can easily get files longer than 10,000 lines so you need something to break them up.
Of course use include guards, they'll likely solve the redefining error.
You need to know the difference between a definition and a declaration, and what uses of an entity required the entity to be declared. Then you also need to learn the 'one definition rule' (ODR) which tells you when when you're not allowed to have more than one definition in the program (and therefore the definition can't go in a header) and what things can be defined more than once as long as the definitions are identical (and therefore the definition can go in a header).
For example, those arrays you're declaring; since these are globally visible arrays the program can only contain one definition, and therefore the definition can't go in a header. Every part of the program that needs to access them simply needs to know their declaration. So instead of putting a definition in a header file and violating the ODR, you should have a C++ file that contains their definition and a header that contains declarations for them.
Code like this:
int foo[100];
both declares and defines the array foo. Put code like this in a C++ file. To only declare this array you do this:
extern int foo[100];
Put code like this in a header.
Class definitions, inline functions, and templates are all things that can be defined multiple times as long as the definitions are identical. You can put these definitions into headers, whereas regular functions, and global variables may only be defined once, so you declare them in headers and then define them in implementation files.
I have a template matrix class class defined in a header called "Matrix.h".
Certain matrices are used repeatedly in my program. I thought that I would define these in the "Matrix.h" header file, like so:
const Matrix<GLfloat> B_SPLINE_TO_BEZIER_MATRIX(4, 4, values);
When I do this g++ complains that I redefined the constant in question. This happens because I include Matrix.h in two different source files. When the object files for these are compiled, both end up with a definition of the matrix above, causing the error message.
My question is how do I avoid this situation? I want a constant that is accessible to more than one file, but I don't know where to put it.
You avoid it by:
Declaring it extern in the header. A symbol can be declared any number of times.
Defining it in the implementation, only once.
If you don't want to split it between a header and implementation file,
Declare your constant static (or declare it in anonymous namespace) to make definition private. Linker will not complain, but it will result in multiple private copies across compilation units.
static Matrix<GLfloat> B_SPLINE_TO_BEZIER_MATRIX(4, 4, values);
Make an inline function that returns the constant. Inline function definitions produce "weak" symbols in object file, so linker will eliminate duplicates and pick one.
inline const Matrix<GLfloat>&
GET_B_SPLINE_TO_BEZIER_MATRIX() {
const static Matrix<GLfloat> B_SPLINE_TO_BEZIER_MATRIX(4, 4, values);
return B_SPLINE_TO_BEZIER_MATRIX;
}
just write your header file like this
#ifndef HEADER_FILE_NAME_H
#define HEADER_FILE_NAME_H
// your header file code
#endif
this will make sure that it won't get declared multiple times
Wrap header files (.h) in preprocessor conditionals to prevent them from being included in the compiler's symbol table twice:
#ifndef HEADER_NAME
#define HEADER_NAME
// code...
#endif//HEADER_NAME
HEADER_NAME can really be anything, but it's best to make sure that it's something related to the file to prevent more collisions, as this is just defining an empty preprocessor macro (which also ends up in the symbol table).
I have a character array defined in a header
//header.h
const char* temp[] = {"JeffSter"};
The header if #defined guarded and has a #pragma once at the top. If this header is included in multiple places, I get an LNK4006 - char const * * temp already defined in blahblah.obj. So, I have a couple of questions about this
Why does this happen if I have the guards in place? I thought that they prevented the header from being read in after the first access.
Why do the numerous enums in this header not also give the LNK4006 warnings?
If I add static before the signature, I don't get the warning. What are the implications of doing it this way.
Is there a better way to do this that avoids the error, but lets me declare the array in the header. I would really hate to have a cpp file just for an array definition.
Why does this happen if I have the guards in place? I thought that they prevented the header from being read in after the first access.
Include guards make sure that a header is included only once in one file (translation unit). For multiple files including the header, you want the header to be included in each file.
By defining, as opposed to declaring variables with external linkage (global variables) in your header file, you can only include the header in once source file. If you include the header in multiple source files, there will be multiple definitions of a variable, which is not allowed in C++.
So, as you have found out, it is a bad idea to define variables in a header file for precisely the reason above.
Why do the numerous enums in this header not also give the LNK4006 warnings?
Because, they don't define "global variables", they're only declarations about types, etc. They don't reserve any storage.
If I add static before the signature, I don't get the warning. What are the implications of doing it this way.
When you make a variable static, it has static scope. The object is not visible outside of the translation unit (file) in which it is defined. So, in simple terms, if you have:
static int i;
in your header, each source file in which you include the header will get a separate int variable i, which is invisible outside of the source file. This is known as internal linkage.
Is there a better way to do this that avoids the error, but lets me declare the array in the header. I would really hate to have a cpp file just for an array definition.
If you want the array to be one object visible from all your C++ files, you should do:
extern int array[SIZE];
in your header file, and then include the header file in all the C++ source files that need the variable array. In one of the source (.cpp) files, you need to define array:
int array[SIZE];
You should include the header in the above source file as well, to allow for catching mistakes due to a difference in the header and the source file.
Basically, extern tells the compiler that "array is defined somewhere, and has the type int, and size SIZE". Then, you actually define array only once. At link stage, everything resolves nicely.
Include guards protect you from including the same header into the same file repeatedly - but not from including it in distinct files.
What happens is that the linker sees temp in more then one object file - you can solve that by making temp static or putting it into an unnamed namespace:
static const char* temp1[] = {"JeffSter"};
// or
namespace {
const char* temp2[] = {"JeffSter"};
}
Alternatively you can use one source file which defines temp and just declare it as extern in the header:
// temp.cpp:
const char* temp[] = {"JeffSter"};
// header.h:
extern const char* temp[];
Header guards have absolutely nothing to do with preventing multiple definitions in your entire program. The purpose of header guards is to prevent multiple inclusion of the same header file into the same translation unit (.cpp file). In other words, they exist to prevent multiple definitions in the same source file. And they do work as intended in your case.
The rule that governs multiple-definition issues in C++ is called One Definition Rule (ODR). ODR is defined differently for different kinds of entities. For example, types are allowed to have multiple identical definitions in the program. They can (and most always have to) be defined in every translation unit where they are used. This is why your enum definition does not result in an error.
Objects with external linkage are a completely different story. They have to be defined in one and only one translation unit. This is why your definition of temp causes an error when you include the header file into multiple translation units. Include guards can't prevent this error. Just don't define objects with external linkage in header files.
By adding static you give your object internal linkage. This will make the error disappear, since now it is perfectly OK from ODR point of view. But this will define an independent temp object in each translation unit into which your header file is included. To achieve the same effect you could also do
const char* const temp[] = { "JeffSter" };
since const objects in C++ have internal linkage by default.
This depends on whether you need an object with external linkage (i.e. one for the entire program) or an object with internal linkage (unique to each translation unit). If you need the latter, use static and/or extra const (if that works for you) as shown above.
If you need the former (external linkage), you should put a non-defining declaration into the header file
extern const char* temp[];
and move the definition into one and only one .cpp file
char* const temp[] = { "JeffSter" };
The above declaration in the header file will work for most purposes. However, it declares temp as an array of unknown size - an incomplete type. If you wish to declare it as an array of known size, you have to specify the size manually
extern const char* temp[1];
and remember to keep it in-synch between the declaration and definition.
I respectfully disagree with the advice against defining variables in headers, because I think "never" is too broad. Nevertheless, the episode that brought me to this thread offers a cautionary tale for those who dare to do so.
I landed on this page as the result of an inquiry into the cause of warning LNK4006, calling out a long established array that I just moved from the translation unit that defines my DLLMain routine into the private header that is included in most of the translation units that comprise this library. I have compiled this library hundreds of times over the last 11 years, and I had never before seen this warning.
Shortly after I read this page, I discovered the cause of the error, which was that the definition was outside the guard block that protects everything else that is defined in the module that also defines DLLMain, which is where I usually gather all the memory blocks that need external linkage. As expected, moving the table inside the guard block eliminated the warnings, leaving me with only two, related to a brand new externally linked table, to be resolved.
Takeaway: You can define variables in headers, and it's a great place to put common blocks, but mind your guards.
Hang on... you are mixing up your declarations...you did say 'char const * * temp' yet in your header file you have 'const char* temp[] = {"JeffSter"};'.
See section 6.1 of the C FAQ, under 'Section 6. Arrays and Pointers', to quote:
6.1: I had the definition char a[6] in one source file, and in
another I declared extern char *a. Why didn't it work?
A: In one source file you defined an array of characters and in the
other you declared a pointer to characters. The declaration
extern char *a simply does not match the actual definition.
The type pointer-to-type-T is not the same as array-of-type-T.
Use extern char a[].
References: ISO Sec. 6.5.4.2; CT&P Sec. 3.3 pp. 33-4, Sec. 4.5
pp. 64-5.
That is the source of the problem. Match up your declaration and definitions. Sorry if this sounds blunt, but I could not help noticing what the linker was telling you...