How to have a header file without a cpp one? - c++

My header file contains, among other things:
#define PAUSE system("pause");
typedef unsigned char uint8;
static const double PI = 3.14159265358979323846;
static const double oneDegInRads = PI / 180;
I've been including this header file into many .cpp files all over the place without a single problem. As I want to clean up my code I was fixing warnings, mostly minor stuff like "cast double to float, possible loss of data", or "unsigned to signed mismatch" warnings. So I turned on the "Treat compiler warnings as errors" in the settings, so by using that I can have a strict assessment of how bad my code is and fix it accordingly. With it turned on, my solution won't build, and shows the error:
Code Description File
C2220 "Warning treated as error - no 'object' file generated myDefinitions.h
I know why this is happening, as I turned that specific setting on. I have tried suppressing and disabling this warning with:
#pragma warning (disable : 2220)
And I've tried also following the "One CPP for each header rule", making a "myDefinitions.cpp" and including only the header and nothing else, but the error message still comes up.
So my questions are:
1: Can I have a header file without a .cpp one (without ignoring the warnings)?
2: If not, how do I make my .cpp, as I've already tried but failed?
3: What better solution can you suggest to have one page where all your important definitions that you use very frequently are? I need to make it possible to include them anywhere you want.

Visual Studio is trying to compile your myDefinitions.h header file to an object file.
It should not do that! Only .cpp source files should be translated to object files.
I guess you probably renamed a .cpp file to myDefinitions.h at some point, and Visual Studio didn't understand you wanted to change its file "type".
Try to delete your myDefinitions.h file, and then create a new myDefinitions.h file, choosing the correct file type from the new file dialog. You can then put the old content into that new header.

OK, thank you to both Ton Plooij and Johan Boule. The reason this was happening was that in my header file there were implicit type conversions such as:
C4305: 'initializing': truncation from 'double' to 'float'
In the Error tab it only said:
"Warning treated as error - no 'object' file generated
Which led me believe that it was LOOKING FOR a CPP file, which is strange because header files aren't made into object files. What I didn't know is that I could find the "Warning" that triggered the "Error" message by clicking on the "Warnings" tab. And it showed exactly which "Warnings" made the "Error" show up.
Thanks again for your help.

The C2220 error occurs because there are warnings. Since there are warnings, no object or executable will be generated. You can't disable this C2220, it's what you enabled with the /WX option. So, either fix all warnings or disable the /WX (Treat all warnings as errors) option.

Related

Changing project's dirs breaks precompiled file creation

I use MSVC2017 (with MSVC2013 toolchain, if it's matters).
So, I have created new solution with "static lib" project and a console app. At this step it works.
Now, I changed some project's paths for the lib project:
Output directory: $(SolutionDir)BuildDebug
Intermediate directory: $(OutDir)\Debug
I added following includes into pch.h:
#include <windows.h>
#include <inttypes.h>
#include <cstdlib>
#include <stdexcept>
I added reference to my lib and lib's include dir inside console app. Now Studio cannot compile my project, showing a lot of errors about
error C2061: syntax error: identifier 'LONG'
and related.
I found that there is no .pch file anywhere.
I also created test solution with same static lib alone and changed same paths. It seems to compiling successfully, but Intellisense underlines "LONG" with red, saying "it's undefined".
May be someone faced the same problem.
Update: I just tried to create a new solution. I added static lib project, then I added simple file with single function int func(LONG v). It seems to compile. But then I add console app to the solution, link it against static lib, and it's not compile, saying that
error C2065: 'LONG': undeclared identifier
Update 2: I've found that static lib files don't see <windows.h> added into precompiled header. So I included it into my header directly and added typedef struct IUnknown IUnknown; before windows.h, because of new error related to IUnknown. It seems to work. But I still don't understand what is going on.
"Pre-compiled headers" are a build-speed optimization. If they're giving you problems, you can always turn off their use temporarily. When they're turned off, the .pch is no longer used, but the .h is still used.
I expect you'll still have the missing LONG, since it's not even in the .h
For your sanity, it might be useful to use explicit names for your precompiled .h. I'm not sure if VS2017 already uses pch.h by default, or it it still uses stdafx.h. Either way, that's just a default. If you want, you can also rename them to staticlib.h/.pch and executable.h/.pch to avoid confusion. The compiler has no default name for the pch; it relies on compiler switches /Yc (create) and /Yu (use).

Visual C++ Express 2010 suddenly won't accept #includes

I'm working with an API which has #defineed all their include files. I'm developing in Visual C++ 2010 Express, and it's been working fine up till now.
I was adding a new cpp-file to the project, and accidentally added a "Windows Form" instead. VC warned me that my project was not using CLR at the moment, did I really want to? I clicked no, and added the file as intended. After that, however, my project no longer compiles.
The code looks basically like this:
api_header.h:
#define DEFINED_HEADER_NAME "path/to/header/file.h"
stdhpf.h:
#include DEFINED_HEADER_NAME
As I said, worked fine for a long time. Now I get this:
error C2006: '#include' : expected a filename, found 'identifier'
fatal error C1083: Cannot open include file: '': No such file or directory
What is causing this? I found some post that said it was because of having turned on precompiled headers, but I checked Project properties > Configuration properties > C/C++ / Precompiled headers, and it's off (I mention the setting path since I'm new to VS, there might be more than one way to do it...).
Any ideas?
The problem almost certainly lies in the order in which the two statements are pre-processed, rather than having anything to do with inadvertently adding a Windows Form object.
This knowledge base article suggests:
The problem is in using a defined constant to specify an include file in the #include directive. The directive is being processed before the macro is completely expanded, resulting in the error.
The second error seems to confirm this, as it indicates the pre-processor is searching for an include file with an empty name:
fatal error C1083: Cannot open include file: '': No such file or directory
The order of your include files has changed. Perhaps Visual Studio inserted a #include "stdhpf.h" somewhere ahead of your #include "api_header.h".
Disable precompiled headers. It should helps.

How to fix header file error?

So, my question is how to fix some error in header file, to run program normally? For example I use c++ builder 2010 and when winuser.h file is included, the program always get error like this
Checking project dependencies...
Compiling Project7.cbproj (Debug
configuration) [BCC32 Error]
winuser.h(47): E2257 , expected Full
parser context
File6.cpp(4): #include c:\program files (x86)\embarcadero\rad
studio\7.0\include\winuser.h [BCC32
Error] winuser.h(48): E2257 , expected
Full parser context
i try to replace that file with original from default installation, but that still get same error, how to fix that?
The error is almost certainly caused by whatever code appears before line 4 of File6.cpp. Most likely that is another header file, in which case it is likely that the code therein is malformed - a missing semicolon or brace for example.
The quickest way to verify that winuser.h is not the issue is to change the order of inclusion so that winuser.h is included first.
Another possibility is that something in winuser.h is dependent on some other header not previously included or directly included in winuser.h. Most Win32 API headers are included by windows.h, and it is generally advisable to include windows,h rather than either of its children.
The message is hard to read but the actual error is "E2257 , expected" (coma expected)
From the RAD studio documentation:
A comma was expected in a list of declarations, initializations, or parameters.
This problem is often caused by a missing syntax element earlier in the file
or one of its included headers.
The error message give you the line where it happened and you should probably look before that. There is probably some '}', ')' or ';' or other syntaxic closer missing in your code just before the error (likely before inclusion of the header file in your code). Full error message (you truncated it) or actual code would make it easier to spot.
It is also possible, even if unlikely, that the error is in one of the headers included in winuser.h.

What is a .h.gch file?

I recently had a class project where I had to make a program with G++.
I used a makefile and for some reason it occasionally left a .h.gch file behind.
Sometimes, this didn't affect the compilation, but every so often it would result in the compiler issuing an error for an issue which had been fixed or which did not make sense.
I have two questions:
1) What is a .h.gch file and what is one used for? and
2) Why would it cause such problems when it wasn't cleaned up?
A .gch file is a precompiled header.
If a .gch is not found then the normal header files will be used.
However, if your project is set to generate pre-compiled headers it will make them if they don’t exist and use them in the next build.
Sometimes the *.h.gch will get corrupted or contain outdated information, so deleting that file and compiling it again should fix it.
If you want to know about a file, simply type on terminal
file filename
file a.h.gch gives:
GCC precompiled header (version 013) for C
Its a GCC precompiled header.
Wikipedia has a half decent explanation, http://en.wikipedia.org/wiki/Precompiled_header
Other answers are completely accurate with regard to what a gch file is. However, context (in this case, a beginner using g++) is everything. In this context, there are two rules:
Never, ever, ever put a .h file on a g++ compile line. Only .cpp files. If a .h file is ever compiled accidentally, remove any *.gch files
Never, ever, ever put a .cpp file in an #include statement.
If rule one is broken, at some point the problem described in the question will occur.
If rule two is broken, at some point the linker will complain about multiply-defined symbols.
a) They're precompiled headers:
http://gcc.gnu.org/onlinedocs/gcc/Precompiled-Headers.html
b) They contain "cached" information from .h files and should be updated every time you change respective .h file. If it doesn't happen - you have wrong dependencies set in your project

Why is C++Builder failing to create pre-compiled headers?

Problem
In CodeGear C++Builder 2009 we are using the pre-compiled header injection to greatly reduce our compile times. We have the same header file being injected into multiple projects. When compiling some projects, the compiler kicks out the following warning:
[BCC32 Warning] Dateutils.hpp(43): W8058 Cannot create pre-compiled header: initialized data in header
In this example, the Dateutils.hpp is the file it's complaining about (CodeGear's header). I've seen this happen with other headers as well. What makes this interesting is that this only happens with some projects (same header being injected).
In the past, I've had to just find the header who ultimately included this errant file and remove it from my pre-compiled header file. Does anyone know what's going on here and the best way to fix it?
Update
I ended up performing a process of elimination approach to the header file and came up with an interesting finding that I cannot explain. Out of the 50+ headers that get included, when I removed vcl.h I no longer get the W8058 warnings. I do not understand this as I would imagine that this header file in particular is a prime candidate for pre-compiliation. Can anyone explain that?
One thing that may be related is the way default string parameters are handled by BCB 200x.
Functions declared like this give the "can't generate precompiled header" message.
void myFunc(const AnsiString &param="");
However, change it to this, and the precompiled header can be generated.
void myFunc(const AnsiString &param = AnsiString(""));
In my experience, that warning message is misleading. It seems that the compiler identifies "candidates" where a header might have initialized data, then when it determines that the file is actually ok, it goes on. If it doesn't find another candidate, it won't show the message. If it finds another candidate that turns out to be a real problem, it then shows the message about the first candidate.
This makes identifying the real culprit extremely difficult.
There are VCL header files that have this known issue: QC 23002. The marked severity on this item though is a "minor failure."
So the workaround options are limited:
Not using those header files (which, yes, does defeat the idea)
Modify the header files (not advisable -- hard to track changes, keep them current).
Either way, make sure that of the ones you come across, CodeGear has knowledge of those header files having that issue. That will certainly be the best way to address it long term -- let the vendor fix their problem. Supposedly CodeGear has DateUtils.hpp in their internal tests for this, but that was posted (for QC 2781) in July 2007. If the problem or certain header files affect you considerably, contact them about it.
I get this warning message when the code shows:
#include <vcl.h>
#pragma hdrstop
I found a simple fix by swapping these lines to:
#pragma hdrstop
#include <vcl.h>
Warning no longer appears.