I have a very large codebase (read: thousands of modules) that has code shared across numerous projects that all run on different operating systems with different C++ compilers. Needless to say, maintaining the build process can be quite a chore.
There are several places in the codebase where it would clean up the code substantially if only there were a way to make the pre-processor ignore certain #includes
if the file didn't exist in the current folder. Does anyone know a way to achieve that?
Presently, we use an #ifdef
around the #include
in the shared file, with a second project-specific file that #defines whether or not the #include
exists in the project. This works, but it's ugly. People often forget to properly update the definitions when they add or remove files from the project. I've contemplated writing a pre-build tool to keep this file up to date, but if there's a platform-independent way to do this with the preprocessor I'd much rather do it that way instead. Any ideas?
Create a special folder for missing headers, and make that folder to be searched last
(that is compliler specific - last item in "INCLUDES" environment variable, something like that)
Then if some header1.h can be missing, create in that folder a stub
header1.h:
Now you can always write
So far as I know cpp does not have a directive regarding the existence of a file.
You might be able to accomplish this with a bit of help from the Makefile, if you're using the same make across platforms. You can detect the presence of a file in the Makefile:
As @Greg Hewgill mentions, you can then make your #includes be conditional:
Generally this is done by using a script that tries running the preprocessor on an attempt at including the file. Depending on if the preprocessor returns an error, the script updates a generated .h file with an appropriate #define (or #undef). In bash, the script might look vaguely like this:
A pretty thorough framework for portably working with portability checks like this (as well as thousands others) is autoconf.
I had to do something similar for the Symbian OS. This is how i did it: lets say you want to check if the file "file_strange.h" exists and you want to include some headers or link to some libraries depending on the existance of that file.
first creat a small batch file for checking the existence of that file.
autoconf is good but an over kill for many small projects.
----------check.bat
----------check.bat ends
then i created a gnumake file
----------checkmedialist.mk
----------check.mk ends
include the check.mk file in your bld.inf file, it MUST be before your MMP files
now at compile time the file
file_strange_supported.h
will have an appropriate flag set. you can use this flag in your cpp files or even in the mmp file for example in mmpand in .cpp
Contrary to some claims here and on the internet, Visual Studio 2015 does NOT support the
__has_include
feature - at least according to my experience. Tested with Update 3.The rumors may have arisen from the fact that VS 2017 is also referred to as "Version 15"; VS 2015 is instead referred to as "Version 14". Support for the feature seems to have been officially introduced with "Visual Studio 2017 Version 15.3".
Another possibility: populate a directory somewhere with zero-length versions of all of the headers you wish to optionally include. Pass a -I argument to this directory as the last such option.
The GCC cpp searches its include directories in order, if it finds a header file in an earlier directory it will use it. Otherwise, it will eventually find the zero-length file, and be happy.
I presume that other cpp implementations also search their include directories in the order specified.