C++ Don't include includes from previous header - c++

Say I have the following:
Main.cpp
#include <Windows.h>
#include "B.h"
...
-
B.h
...
SomePrototypeFunctionNeedingWindowsH();
-
In B.h, I'm not required to include Windows.h again as it's already been included beforehand. For clarity, I would like to be required to include Windows.h for each new file that wants it. I'm using VS2015.
Can this be done?
Can this be done without impact on compilation time?
Would this be considered an acceptable practice?
Will I run in to any issues if this was done?

Maybe you're looking for the preprocessor directives in C++.
They are something like:
#ifndef HEADERFILE_H
#define HEADERFILE_H
/*Your header declarations/definitions*/
#endif
In this preprocessor technique, you basically tell your compiler that it should not include the same header for multiple times.
Refer to this post for more thorough understanding

Compile each .h file into throw-away test output .objs. This can be done manually, or through a script to run on whatever project management system you use.
Naturally something has to add the .h files to the project management system.
A .h file that can be compiled as a source file includes all the header files it needs.
The exact steps -- you could iterate through each .h inmthe directory tree, output a .h.cpp file, add that .h.cpp file to a project that you do not otherwise use, and build that project.
What language ypu write this in depends on what scripting languages you are good at.

Related

C++ preprocessor executing both #ifdef and #ifndef

So I'm currently working on something that uses OpenCL. The OpenCL spec provides the users with a directive which must be included before the inclusion of the header (cl.h)
#define CL_TARGET_OPENCL_VERSION 110
Which basically defines the version they want to use. Suppose I'm making a library and I want my users to define this instead of me defining this inside my files. What I did was.
-----main.cpp---
#define CL_TARGET_OPENCL_VERSION 110
#include "library.h"
-------x---------
----library.h-----
#ifdef CL_TARGET_OPENCL_VERSION
#pragma message("def")
#endif
#ifndef CL_TARGET_OPENCL_VERSION
#pragma message("ndef")
#endif
.... include other headers.
--------x---------
And the compiler prints both def and ndef messages. And the OpenCL library also throws a warning that it's undefined. I thought that the library header would get substituted into main and it'd only print the def message. Is there anything I understood wrong?
I'm particularly confused as to where does the preprocessor start? If it starts from main.cpp and goes from top to down, then it surely has defined the macro. After that it sees the library inclusion, then it should only print the def message but it prints both.
This leds me to believe the preprocessor does scan the header file before including it in main? Dunno the reason why. Also I have assured that the library header isn't included elsewhere.
One interesting thing I noticed was, if i did this
-----helper.h---
#define CL_TARGET_OPENCL_VERSION 110
-------x---------
----library.h-----
#include helper.h
#ifdef CL_TARGET_OPENCL_VERSION
#pragma message("def")
#endif
#ifndef CL_TARGET_OPENCL_VERSION
#pragma message("ndef")
#endif
.... include other headers.
--------x---------
It prints the def message "twice". If anybody can explain all this I'd be grateful.
EDIT:- The files I'm compiling are main.cpp library.h and library.cpp
Library.cpp includes library.h from the start as usual. Maybe this other cpp is causing the problem?
In C/C++ programs, the compiler handles each .c and .cpp file separately.
The compilers build each source file (NOT the header files, only .c and .cpp files) independently from each other (this source files are called compilation unit).
Thus, when your main.cpp is built, the compiler finds the #define CL_TARGET_OPENCL_VERSION 110 you have added on top of the main.cpp file, emiting the defmessage.
But when the compiler builds the library.cpp file, it does not find the version define, so it emits the ndef message.
So, following this explanation, it is completely normal that in your last case, when you add the define to the .h file, the compiler emits the def message twice, once for the main.cpp file and once for the library.cpp file.
Now, the problem is where should you add the define, in order to have the program built consistently, with the same version for all the .cpp files.
Usually, all the IDEs have some configuration page where you can add global defines, for all the project, which are "inserted" into all the compilation units before everything else. So when the IDE calls the compiler, it passes the same defines to all the compilation units. You should add this kind of defines in this page.
In your IDE (I am using Code::Blocks, v 17.12), you can find this page in the menu: Project / Build Options
For each type (Debug or Release), you have to go to the tab Compiler Settings, and there to the sub tab #defines. There you can add global defines, which can be different if you are building in Debug or in Release mode (of course, if you set the same in both modes, they would be the same).
Once you have added your define here, please, remove it from the main.cpp, library.h and any other place where you may have added it, in order to avoid duplicities.
From the comments about portability:
You have several options:
Always use Code::Blocks: this would be the easiest way, since you can pass the Code::Blocks project along with the source files, and everything would be already setup.
Use cmake, which is a script build system, where you can set defines and so in the same way as using an IDE. cmake is much widely used than Code::Blocks, so maybe it is a better option.
Add a new options.h header file, where you set all the defines, and include it to all your .c/.cpp. This setup has the additional benefit that for different systems, changing only the options.h file the build can be completely different. This is a manually setup of what the IDE is doing. It has the advantage that does not rely on external tools, but the disadvantage that you have to remember to add it in all the new .cpp files added to the project.
My recommendation is go with cmake, just as the others have said.
Prefer using #ifndef XXXX_h #define XXXX_h #endif over #pragma once
If your #include search path is sufficiently complicated, the compiler may be unable to tell the difference between two headers with the same basename (e.g. a/foo.h and b/foo.h), so a #pragma once in one of them will suppress both. It may also be unable to tell that two different relative includes (e.g. #include "foo.h" and #include "../a/foo.h" refer to the same file, so #pragma once will fail to suppress a redundant include when it should have.
This also affects the compiler's ability to avoid rereading files with #ifndef guards, but that is just an optimization. With #ifndef guards, the compiler can safely read any file it isn't sure it has seen already; if it's wrong, it just has to do some extra work. As long as no two headers define the same guard macro, the code will compile as expected. And if two headers do define the same guard macro, the programmer can go in and change one of them.
#pragma once has no such safety net -- if the compiler is wrong about the identity of a header file, either way, the program will fail to compile. If you hit this bug, your only options are to stop using #pragma once, or to rename one of the headers. The names of headers are part of your API contract, so renaming is probably not an option.
(The short version of why this is problematic to use #pragma is that neither the Unix nor the Windows filesystem API offer any mechanism that guarantees to tell you whether two absolute pathnames refer to the same file.)

How to use google protobuf in a project with precompiled headers

I have a solution which contains several projects. My projects (but not all of them) use precompiled headers. I decided to use protobuf and I've met a problem. After generetaing *.pb.h from *.proto by protoc.exe I'm trying to include the header and get the error - precompiled header wasn't included into *.pb.h.
How I can solve this problem? I have an idea (but I don't like it at all) - after protoc generates *.pb.h I can run some script, which'll include my precompiled header into the *.pb.h. But I don't like it because some projects may not use PCH, and PCH file name can be different.
I understand that I can just remove PCH from my projects, but I don't like that idea too.
Dont add the generated myproto.pb.cc to your project. Instead, create a myproto.cpp with
#include "pch.h"
#include "myproto.pb.cc"
I resolved my problem by creating a static library called proto-objects (without PCH) and including all my *pb.h(cpp) files there. After it I link that library to every project where I need my protobuf objects. Profit!
You can disable the pre-compiled header option on a file-by-file basis.
Given that the pch option is intended to speed up compilation, you can turn it off for the whole project, and no further changes should be necessary.
The choice of name of the header file, and the pch file are also selectable per file in the project
Update
The idea behind Microsoft's Pre-compilation PCH system is to
Speed up compilation
Make it easy to use
The header file system in C/C++ is problematic, as it is really a textual replacement.
That means that
#include "localdefs.h"
#include <windows.h>
#include "project.h"
#include "support.h"
Is in no way similar to
#include <windows.h>
#include "project.h"
#include "support.h"
That is because localdefs.h can redefine the behavior of all of the other includes.
Further to this the costs of walking through the complexities of the windows.h header files, is time consuming.
The PCH system tries to solve this by the observation that most projects have a fixed set of include files which are included by most/all of the CPP files.
Defining this set in stdafx.h allows the textual result of that parsing to be pasted in the cpp file and save a lot of work.
If most of the includes in the project are different, then there is no need to use it.
So if you are including the same qt header files in lots of places - add them to a pre-compiled header file. The more of the common includes added to this file, the better the compile speed improvements will be.
Any non-standard cpp file can be excluded by being specifically disabled - examples are "generated files". Where the template generator does not understand the MSVC system.
If all the files are different, then only limited performance benefit will be gained - as each compile would probably also include a pch recompile.

Definitive way to include files on c++ avoiding cyclic dependencies

I always have problems with c++ on this, I spend more time trying to solve dependencies instead of programming when I setup a new project. I search the internet a way to do this automatic, or softwares that do that. In fact, I always program on geany and compile with shell script files...
So, is there a software to manage this? Do IDE's do that?
I always include .cpp files on my main.cpp and then I include the .hpp files on these .cpp. So, if I have a main.cpp, a object.hpp and a object.cpp, I will include the object.cpp in the main.cpp and the object.hpp on the object.cpp. Is there a better way to do that?
Can I just include the .hpp files and in the build script add every .cpp file?
I just cant find the answer on the internet, maybe im doing the wrong question...
I have found a nice article dealing with including files.
Common practice for all c++ header files is to simply define inclusion guards.
#ifndef TEST_H
#define TEST_H
// class definitions goes here
#endif
If there are some cyclic dependencies, consider forward declaration.
Every-time this header is included, the compiler checks, whether symbol TEST_H has been defined already. This basically guarantees, that contents of this file are included only once, and so that there is single declaration of the classes, defined in header file.
Good to know is, that directive "#include <>" does copy and paste all the contents of the included file.
Including .cpp file is not strictly disallowed, and sometimes good choice, it is considered a bad practice. As I mentioned, including file, means that all contents of the file are being duplicated at the place of inclusion. This is okay, for the header file with inclusion guard, but not okay for .cpp file, since every function definition inside this file, will be duplicated.
Not including file in the build script means, that only the those duplicated data are included in the build, otherwise you would end up with multiple function redefinition errors.
If you are looking for IDE, consider:
Visual Studio
Code Blocks
Eclipse
IDE won't do all the work, but you can be significantly more productive using good IDE.
TLDR:
Use inclusion guards
Include all .cpp files in build script.
Do not "#include" .cpp files.
In every .cpp file, include only needed headers, to reduce compilation time.
I see a lot of good suggestions with good practices but your mistake (including .cpp files from a .cpp file) suggest you're missing some concept in the C/C++ build process, I hope a little explanation would help you understand better and avoid the mistake.
Think of .c .cc .cxx .cpp files as modules, a .cpp file is a module, with your implementation of something, .h .hpp are just headers where usually you don't put implementations but declarations to be shared with multiple modules.
Usually each .cpp module is compiled to a binary object g++ -c -o mymod1.o mymod1.cpp then (once all modules are compiled) linked together g++ -o myprog mymod1.o mymod2.o ....
Even if you compile and link with a single command g++ -o myprog mymod1.cpp mymod2.cpp behind the scene g++ handle each module as single object.
I think is important you understand that each module/object know nothing about others, and if you need some other module (your main.cpp) to know something about mymod1.cpp a header file is required .h .hpp (mymod1.h) with the declarations needed to be shared: module global variables, defines, enums, function prototypes or class declarations, then just include mymod1.h in the module(s) where you want to use something of your mymod1 implementation (main.cpp).
Also, you write you're using a shell script to build, that's ok if your project are few files, better would be to use something like make, learn how to use it will require some time but then I bet geany have some facility to build projects based on Makefiles, make is the way to handle C/C++ projects from a long time.

Get all include files of a cpp file considering preprocessor defines (fast)

I need a tool (command line, script or source code) that extracts all inlcude files that are included by a source file (recursive) with given preprocessor defines and include paths. I want to know the ones that could be found and the one that doesn't. The include files that could be found shall be recursivly parsed.
I know about the
gcc -M /-MM
cl /P
solution, but this does not work for me. The preprocessor stops as soon as it could not open a file. But at this time I don't have the correct path for that files and just want the preprocessor to skip that file and to tell me that it could not include that file
Also the cinclude2dot.pl from here is not useful, because it seems not to consider given preprocessor defines.
Very useful is the include file hierarchy finder from CodeProject. It considers the preprocessor flags and shows me all include files. Even the includes that couldn't be opened. But it is written in MFC and I would have to reimplement this for the gcc what is not such simple because a lot of WinAPI stuff is used even inside the parser.
Thus, maybe some one knows another solution.
an simple example:
main.cpp
#include <iostream>
#include <string>
#include <boost/foreach.hpp>
#include <SharedClass.h>
#include "MyClass.h"
#ifdef FOO
#include <OptClass.h>
#endif
int main() {}
Right now I start the include extraction like (simplified):
.getAllIncludes main.cpp -I includepath1;includepath2 -PD FOO
and obtain:
cannot open //-> I don't care right now, it's a default header
cannot open // -> here I can extract the info that I need boost
SharedClass.h
SharedDependenyClass.h //a header that is included by SharedClass...
MyClass.h
TestClass.h //a header that is included by the MyClass header...
TestClass2.h //a header that is included by the TestClass header...
OptClass.h
and for
.getAllIncludes main.cpp -I includepath1;includepath2
I'll obtain:
cannot open //-> I don't care right now, it's a default header
cannot open // -> here I can extract the info that I need boost
SharedClass.h
SharedDependenyClass.h //a header that is included by SharedClass...
MyClass.h
TestClass.h //a header that is included by the MyClass header...
TestClass2.h //a header that is included by the TestClass header...
I know that the deafault header may also define some values. But in my case I don't need that information, because the project source code doesn't depend on any of that defines. If thus, I feed my tool with this preprocessor define...
In the end the tool works quite well. It runs recursivly over ALL necessary files and in the end I have all needed files for the project. Of course there are some small restrictions I don't want to name then all (e.g. every header of an source file name has the same name, ... ).
Using gcc -M <source_file>, the code is not compiled, it is only processed by the precompiler. And, any solution you may find needs to process the source using the precompiler, to be correct. Imagine that the source, somewhere, has the following snipset:
#ifdef USE_BOOST_SUPERLIB
# include <boost/superlib.hpp>
#endif
then without preprocessing you cannot know if <boost/superlib.hpp> is included.

How to include part of file by C++ preprocessor #include

I want to refer some stable library code which is not maintained by me. Actually it is some MFC code snippet.
But, whenever I want to include the code snippet, I have to #include entire file, which consequently I have to include other stuff, then the whole MFC ... The consequence is not acceptable.
Currently, I copy/paste the code snippet into my project, but I feel disgraceful. Can I just refer part of a file by C++ preprocessor?
Even the code is hard-linked with specific MFC version, it is better than duplicate them in my project. With such hard-link, I will know it's from MFC and save my time to check them.
Is there some super #include usage?
Can we write something like
#include "foo.h" line [12, 55)
which means to include line 22 to 54 for foo.h
What some have done is write #ifdef-sections in their headers to allow including files to only get specific parts. I don't know if your MFC file has those but you can look through it and use any existing ones or write your own.
The header usually look something like this
#ifdef USE_FANCYPANTS
bool hasFancyPants();
#endif
#ifdef USE_COOLSTUFF
void doCoolStuff();
#endif
And your include files then use #define before including.
#define USE_FANCYPANTS
#include "header.hpp"
Then you only get hasFancyPants() and not doCoolStuff()
You can use conditional compilation to inlcude/exclude stuff you dont need. You have to change the source code slighty, and amend project settings.
Can use typedef keyword, which would define types differently for MFC and non-MFC, and/or specific to your project settings, and the legacy code.
You may put entire stuff in a DLL or a .LIB (having code, not just declaration), and put the linker pragma in header file itself.