How to deal with precompiled headers randomly becoming corrupted on a cancelled build? - c++

I use Visual C++ 2012 with a project that makes a heavy use of precompiled headers. So heavy that the infamous /Zm switch is in use.
When I cancel a build in progress, I sometimes get this error on the next build:
error C1852: 'foo.pch' is not a valid precompiled header file
Nine times out of ten, things will go smoothly, but when this happens I have to find the .pch and delete it manually before restarting the build.
That annoys me a bit. Is there a way to prevent this from happening? A patch from Microsoft? Or a way to force Visual to delete the .pch and restart the build automatically when the issue occurs? Or some other solution I didn't think about?
EDIT: Here's the version of Visual I'm running:
Microsoft Visual Studio Professional 2012
Version 11.0.61030.00 Update 4

This is a pure conjecture, as I did not run into this issue.
Try to find out how Visual detect a .pch file is corrupted (i.e. empty file, file not correctly ended, ...). If it follow a clear pattern, write a pre-build script that parse all .pch and delete corrupted ones.

I would create a script that would attempt to recompile the stdafx.cpp file, but this time using the PCH instead of generating it. I.e. the expected outcome is the successful compilation of an empty file. If this fails, delete the PCH. Now run this script as a pre-build step.
It sounds fairly expensive, but it's very reliable. Any problem loading the PCH causes its regeneration, even compiler upgrades. Also, your PCH is now in file cache, which means the actual use is slightly cheaper.
This might be implemented as an NMAKE build script with somewhat unusual rules.

I followed rockeye's suggestion of trying to find a pattern in these corrupted files. Turns out it's very simple: valid files start with a VCPCH0 header, corrupted files don't.
A simple C# program run as a Pre-Build Event of the failing project(s) and deleting the corrupted files solves the issue. If anyone's interested, the source is right here.

Related

Visual Studio : compile list of modules on each platform and configuration

I am working on a huge C++ project, targeting many platforms with several configurations for each platform.
Because of the long compilation time, build the entire project on every platform to test if a change compile successfully, isn't an option.
What I usually do, is compile the single cpp modules I modified on different combination of platform/configuration.
I'd like to automate this process, either using a script, a VS extension, whatever, I am open to evaluate different options.
What I need exactly is taking a list of cpp files and compile each file, for each platform and each configuration (basically iterating through all combination of the configuration manager).
Is this possible? any good suggestion on how to approach the problem?
EDIT:
I am aware that this is way far to be a perfect solution, and will spot only a subset of errors.
I will still have to face linking errors, compiler errors on other cpp units depended on a modified header, and so on..
I also, don't have any chance to modify the current build system, or project generation.
I am mostly interested in a local solution, to reduce the amount of possible issues and facing the huge building time process.
EDIT2
We have a build system. This has to be considered a pre-build system optimization, for my personal workflow.
Reasons:
Triggering a build system job requires time. It will be the final step, but instead of spending hours waiting, and maybe discover later that a given compiler on a given platform for a specific configuration raise an error, it would be much more efficient to anticipate those findings as much as possible.
Current manual workflow:
Open each cpp file I modified
Compile each cpp file as a single unit (not building the project. On VS Build-> Compile)
Change Platform and/or configuration and re-do point 2 again.
This is the manual workflow I'd like to optimize.
I would suggest that you "simply" write a script to do this (using Python for instance, which is very powerful for this kind of this)
You could:
Parse the .sln file to extract the list of configurations, platforms ( GlobalSection(SolutionConfigurationPlatforms) entry) and projects (Project entry)
If needed, you can parse every project to find the list of source files (that's easier than parsing the .sln, as vcxproj files are in xml). Look for ClCompile xml nodes to extract the list of .cpp files.
Then you can identify which projects needs some files to be recompiled (getting list of modified files as script input parameter or based on timestamp checking)
Finally, to rebuild, you have two options:
Call "msbuild " to recompile the whole project (vcxproj) (for instance msbuild project.vcxproj /p:Configuration=Debug;TargetFrameworkVersion=v3.5)
You could also recompile a single file (cl simple.cpp). To do so, you need to know what are the cl build options to be sure you compile the file exactly the same way as Visual Studio would. If you earlier did a full build of the solution (it could be a rquirement for your script to work), then you should be able to find that from Visual Studio logs (within the target folder). In my solutions, I can find for every project (vcxproj file) a build log per configuration (in %OUTPUT_DIR%\lib\%libname%\%libname%.dir\%configuration%\%libname%.tlog\CL.command.1.tlog), this file reports the exact cl arguments that were used to compile every file of the project. Then you can manually invoke cl command and this should end up recompiling the file the same way Visual Studio would do it.
Additionnaly, you could add a project in your Visual Studio solution that would fire this script as a custom command.
Such a script should be able to identify which projects has to be rebuilt and rebuild them.
This is a very common requirement, it is never solved this way. What you are proposing is not completely impossible, but it is certainly very painful to implement. You are overlooking what should happen when you modify a .h file, that can force a bunch of .cpp files to be recompiled. And you are not considering linker errors. While you'll have a shot at discovering .cpp files, discovering #include file dependencies is very gritty. You can't get them from the project or make file. Compiling with /showIncludes and parsing the build trace files is what it takes. Nothing off-the-shelf afaik.
Don't do this, you'll regret it. Use the solution that everybody uses: you need a build server. Preferably with a continuous integration feature so the server kicks-off the build for all target platforms as soon as you check-in a code change. Many to choose from, this Q+A talks about it.

Visual Studio warning about copies of files with different contents

When I go to debug my C++ project in Visual Studio, up pops a little warning dialogue box that tells me:
A copy of datum.h was found in
c:/users/brad/desktop/source/binary/datum.h, but the current
source code is different from the version built into
c:/users/brad/desktop/source/binary/datum.h.
I'm having trouble understanding what this is even trying to tell me, let alone how to fix it. At first I thought it might be complaining that I'd accidentally duplicated a file in the directory, which I checked, and found nothing of the sort, which leaves me pretty stumped. I also tried excluding the file from the solution and adding it again, which didn't fix the problem either.
The warning doesn't appear to actually hinder the development of my project, but I suppose warnings exist for a reason, so if anyone knows what's gone wrong, any advice would be greatly appreciated. To my knowledge, I didn't change anything to cause the message to appear, it just popped up one time I went to debug the solution and has kept on appearing ever since.
Also, more copies of the same warning have started popping up, pertaining to other header files in my solution (I haven't recieved any about .cpp files yet, but it could be a coincidence, because it's only been going on for about 20 minutes).
Try removing breakpoints from the file in question.
This worked for me when it occurred with Visual Studio 2013 for a header file in debug build.
Source: Release mode file sync issue - current source code different from the version built
Additional notes: Clean / Rebuild also works, but that is painful for regularly changing code. Enabling the break point after starting debugger merely delays the message.
I solved it:
Close the window of the .h file in Visual Studio if it's open.
Close Visual Studio.
CUT the .h file from its normal location and paste it into a temporary folder that VS doesn't know about.
Restart VS and compile. It'll complain about the missing .h file. Good -- Make the bastard beg for it!
Paste the .h file back into its original location.
Compile. VS will gratefully accept the missing file. (Damn I hate Microsoft!)
This occurs if you rename an implementation file (*.c, *.cpp, etc.) to a header file.
This is because the Item Type still remains as C/C++ Source File, making it get compiled as a separate translation unit rather than as an actual header, preventing Visual Studio from recognizing its inclusion as a header elsewhere.
It took me quite a while to figure this out.
To fix this:
Right-click your header file in Solution Explorer and select Properties.
Select All Configurations, All Platforms.
Under General, change Item Type to C/C++ Header.
Press OK.
Force-recompile any file that #includes your header (or just Rebuild the solution).
The problem is that the debugger thinks that the checksum of the source file is different from what the compiler calculated and put in there. The debugger will then refuse to apply breakpoints in the files that mis-match, to prevent you from seeing data it can't guarantee is correct.
I have had this keep happening even after a clean rebuild. This is with VS 2015. My guess is perhaps the debugger and the compiler disagree on how to hash newlines or something like that? The fix is to turn off "require source files to exactly match the original version" in Debug -> Options -> Debugging -> General
Could you by any chance be debugging another executable (not the one actually built?). This is a common issue in scenarios where Visual Studio builds the binaries in one directory but then they are copied over to some other directory for debugging. I'd suggest you compare the target path under the debugging settings and the output directory under the general settings in Visual Studio.
This would explain the issue, since you are actually debugging some older version of the binary (not the one built currently) and thus the warning, since Visual Studio can't find the version of the source files for that version of the binary.
The reason may be circular header dependencies. datum.h may includes another_header.h (directly or indirectly), which includes datum.h.
I see the real reason of this question is not answered. So for someone still looking, here it goes...
The most common reason of this problem is that the source files used to build the existing obj files are different than the existing ones. In other words the
particular project did not build after new modifications to source. The solution to this problem is to rebuild the project after modifying.
This happened to me in situation where I had modified my static library projects files and then without building that project I started my application project which was using this static library project.
this worked for me:
close VS
delete *.vcxproj.filters file
restart VS
problem should be gone.
this worked for me:
clean project
debug/delete all breakpoints :)
This worked for me (as of March 2019):
Click the 'Build' drop-down menu in the top left of your Visual Studio window
Select 'Rebuild Solution'
I've changed the file name and it works now.
Just encountered this. In my case, one of my .h files contained implementation (a class with static methods), which was #included by one of my .cpp files, but the Project Settings were also telling Visual Studio to compile the .h file.
I manually edited both the .vcxproj and .vcxproj.filters project files, moving the .h file from the <ClCompile> ItemGroup to the <ClInclude> ItemGroup.
This did the trick for me; I never saw the "A copy of...is different from..." pop-up again.(Note that this was after I had thoroughly failed in attempts to get <DependentUpon> to work.)
My solutiion:
Build -> Configuration manager
Switch to another configuration (any, example Releas or Debug)
Switch to previous configuration
It is possible to have multiple projects, each with their own entry point within a solution. Make sure that the correct project is being run.
The source code is different message can appear in a project A's source when you are running project B. In this case, the message can mean This breakpoint won't be hit because you're running a project that doesn't include it

Visual studio 2010 c++ won't compile changes, must always clean

It been happening for a while now, that every time I make changes to my code and compile, the behavior of program won't reflect the changes I made. What i have to do to get a change is to clean my project and compile all the files again. Visual studio shouldn't be doing this and its starting get in the way of actually debugging my code to begin with as the program is large and it takes a while to compile.
How can I fix this so I don't have to go through this ritual of cleaning then compiling just to see changes.
Aren't your sources on some network/mounted drive? That may confuse the build.
My experience is that it can miss a dependency with some 1% chance on random files, but no more than that.
If they are not, in options/build&run you can set diag level of build to higher and see what steps are considered for build. Also you can look the discovered depencencies in the intermediate files folder, the .tlog files. You may also try to look at debug output as described here though most of the latter belongs to discovering excess compilations...

Visual Studio Project out of date

I've been trying to get Visual C++ working, but I'm getting this error when building every project: "This project is out of date" "Would you like to build it?" It fails to build every time.
When I rebuild, the build still fails, although in the logger I don't notice any error messages, which makes me think its not logging properly (I'm using a third party program to log).
I've followed some of the instructions here: http://blogs.msdn.com/b/vsproject/archive/2009/07/21/enable-c-project-system-logging.aspx and enabled logging.
I'm getting this error: project not up to date because "insert file name here".lastbuildstate is missing. Note that in actual visual studio, there is nothing logged. I was unable to find anything on this in google. It may be that I incorrectly enabled logging, but I feel that this is the error.
You should let Visual Studio tell you why it needs to rebuild. Visual Studio 2015 has built in support for this:
Tools (menu)
Options
Project and Solution
Build and Run
Change MSBuild project build output verbosity to Detailed or Diagnostics.
In my case it printed a message like this:
1>------ Up-To-Date check: Project: xyz, Configuration: xyz ------
1>Project not up to date because build input 'C:\ws\Missing.h' is missing.
... and removing that header from the project fixed the problem.
To get this information in older Visual Studio versions, you need to use DebugView and modify devenv.exe.config (see Colin Smith's answer: https://stackoverflow.com/a/21759835/1941779). Note that this solution does NOT work for Visual Studio 2015.
What are "tlog" files?
"tlog" files are created by the "Tracker.exe" process which runs while you do a build, and records some information about the build.
That information is used and updated the next time you start a build to help detect "out of date" files, and thus enable the build system to only build the bits that need to be rebuilt (rather than building everything again).
File Tracker Log file format
https://social.msdn.microsoft.com/Forums/vstudio/en-US/67705333-a425-4d6e-9881-9077f044f87a/how-do-i-prevent-msbuild-from-creating-tlog-files-during-my-c-builds?forum=msbuild
https://dickyjim.wordpress.com/tag/tlog-files/
What causes the "out of date" problem?
The problem can be caused by incorrect or stale information in the *.tlog files.
There are 3 main ways that can happen:
1) You built a project on your hard disk, and then moved the directory to another location...the "tlog" files recorded the paths of the old location, yet because you moved the files, they are no longer there, thus you get "out of date".
2) Your "Project" has references to files (usually header files), which do not exist at the location specified. This might occur if you deleted a file from your source control system, but forgot to remove it from your project, or because you refer to header files of a library which might be "installed"/present at a different location. Often, Developers assume files are located at the same "place" on everyones machine....not always the case!
3) You have done some "refactoring" of your project, and moved files around to different subdirectories, or even renamed them - so the paths/names of the files recorded in the "tlog" do not match what exists on your disk i.e. stale.
What is the way to fix it?
Doing a "Clean+Build" or "Rebuild" does not always fix it...as those operations do not delete the "tlog" files. So:
delete any "tlog" files that you can find in your solution/project directories and rebuild.
make sure your Project does not refer to non-existent files
How do I work out which files are non-existent?
If you want to know/find out exactly which files Visual Studio is thinking are out of date, then you can turn on some diagnostic information in Visual Studio....and watch the messages in DebugView...showing the full path of the files it is probing.
http://blogs.msdn.com/b/vsproject/archive/2009/07/21/enable-c-project-system-logging.aspx
In devenv.exe.config you put:
<system.diagnostics>
<switches>
<add name="CPS" value="4" />
</switches>
</system.diagnostics>
More Details
Lets say you created a Solution and a set of Projects in a particular directory e.g. S:\MYPROJECTS, and you compile and run/debug it, etc.
You then decide to move that whole directory to somewhere else on your drive, or you re-factor your Projects e.g. change their directory names, etc.
Now when you do a "Start Debugging/F5", Visual Studio does the depending checking, and thinks you have "out of date files".
Even if you do a "Clean Solution", or a "Rebuild Solution"....you still get the "out of date files" message.
See here:
http://connect.microsoft.com/VisualStudio/feedback/details/653355/suggestion-help-me-diagnose-issues-causing-this-project-is-out-of-date-message
The problem is caused by the ".tlog" files which are being consulted during the dependency checks...when you moved the solutions/projects (along with a builds intermediate files) they cause confusion to the Visual Studio builder.
The solution is to delete all the .tlog files.....they will then be re-generated the next time you do a build...and from that point on you won't get a bogus "out of date files" message....unless they truly are out of date.
I too kept getting "The project out-of-date" error, even though there were no changes. I traced it to a header file listed in Solution Explorer that was no longer being used and had been deleted from the project's directory. Removing it from the SE list fixed the extraneous error message from popping up.
I had this problem, too.
In my case the reason was the references to files (usually header files), which do not exist at the location specified.
I ran into this problem and, using the diagnostics trick that colinsmith posted about, was able to trace the problem back to the fact that my .vcxproj was referencing a file that didn't actually exist anywhere (It had been deleted a long time ago, but never removed from the project file).
Just for posterity, I was getting this problem, and then realized my computer clock had somehow jumped approximately 48 hours into the past. After I set it back to current time, the warning went away.

What does Visual Studio 2010 do before invoking msbuild?

I'm having a problem with Visual Studio not invoking msbuild to actually build my solution. Invoking msbuild from the commandline results in a proper build, but in Visual Studio starting build results in an "everything is up to date" message. Manually compiling a .cpp file seems to partially or fully fix the problem.
Restarting VS2010 does not correct the problem, so I feel like VS2010 must be writing its own dependency information somewhere. By dependency information I mean what files actually require building, AKA which files have been altered since the last successful build.
Does VS2010 perform it's own dependency checking before invoking msbuild? Where does it store this information?
To force a build to occur from the Visual Studio GUI you can select "Rebuild All". That will trigger compilation of all your source files.
The problem with regular builds not working could be related to incorrect clock settings in your PC. Make sure your system clock is correct, including the time zone. Then do a project 'clean' and try to build again.
My Dad says to check your "obj folder" and clean it out. VS2010 is seeing that there are things on there so it assumes there's nothing new to build.
I've seen this kind of behavior occasionally, though I can't explain how it gets corrupted.
Try deleting all the intermediate files: everything in the Debug and Release directories, plus the project name files of types .suo, .ncb, and .aps. Then rebuild all.
If you are experiencing the same behavior as I do, this tends to make VS work properly for awhile—a few weeks or 50-100 builds (whichever comes first).