For those who read this blog and aren't technically inclined or simply don't use Microsoft Visual Studio (e.g. you use a different compiler suite), this entry isn't for you.
One of most annoying things to run into in Visual C++ are linker errors. They are obtuse, poorly documented, and double-clicking them doesn't take you to the source code (or the part of the object file) where the problem is occurring. One of the most confounding error messages is the LNK2005 error message. Usually something like this shows up:
nafxcwd.lib(afxmem.obj) : error LNK2005 ...something about operator new/delete goes here...
If you search Google, a Microsoft Knowledgebase (KB) article pops up (KB148652):
A lot of people run into LNK2005 errors, find the above article, try out what it says, and discover the "solution" makes the problem worse, not better. That is the only KB article I've ever seen that provides an incorrect solution for a problem...usually Microsoft is pretty good about giving right answers.
There are four causes of LNK2005 errors that I've run into and actually fixed:
1) A bad build. For some reason or other VS just occasionally barfs. The solution in this case is to close down VS, wipe all the temporary files (e.g. .obj, .dll, .exe, autogenerated MIDL .c files, etc.), load up VS, and do a Build->Clean Solution, Build->Rebuild Solution. Depending on the size of your solution, this can take a while - go grab a coffee.
2) If it still fails with LNK2005 errors, then something is mismatched. Right-click on each of the projects and select "Properties...". Then make sure the "'C++'->Code Generation->Runtime Library" all say the exact same thing. If you attempt to use different runtime libraries, it may or may not link properly. The reason it will not link is if you allocate memory in one project and then pass it to another project and free it there (sort of like DLLs but weirder). If you are like me and have projects shared between solutions, you will want multiple project compilation types so that you don't have problems with linker errors (I have 6 of 8 possible for my base library - the base library is multi-threaded - I say 8 possible because you have /MD[d] with MFC, which is different than /MD[d]). Once you have types matching (don't forget to match the "use MFC" option if you use MFC!), make sure both debug and release mode are configured correctly with the configuration manager (Right-click on "Solution 'solutionname' (x projects)" and select "Configuration manager..."). Also, make sure the dependencies and build order are correct (same right-click menu but "Project dependencies..." and "Project build order..." instead).
3) If you've done all that and still get LNK2005 errors, then you've hit a scenario I like to call the "duh" scenario. An incorrect entry point for the subsystem selected will raise a LNK2005 error message. So, if you defined main() and don't use /SUBSYSTEM:CONSOLE, you'll get a LNK2005 error. Or if you defined WinMain() and don't use /SUBSYSTEM:WINDOWS, you'll get a LNK2005 error. Again, this doesn't always happen, but when it does it is weird (usually complains about new/delete duplications across object files instead of main()/WinMain()). To change the subsystem, right-click on the startup project and select "Properties...". Then go to Linker->System->SubSystem. Change accordingly to the entry point used.
4) If, even after all that you still get LNK2005 errors, then it is time to scratch your head and think, "Gee, did I or any third party put in any include files that force .lib files to be included in the linking stage?" Start scouring that source code for any #pragma comment(lib, ...) statements. This happens particularly with MFC libraries since there is code floating around out there that forces the MFC libraries to be linked in at link time first and then forces the other libraries to be excluded - including such code with a non-MFC project causes all sorts of headaches since the other libraries are loaded first and thus can't be excluded by the #pragma and then the MFC libraries attempt to get linked in and fail. But it can happen in other cases as well - even indirectly via a third-party library.
I've never experienced this, but according to what people say on the Internet, when they run into LNK2005 errors, they completely rebuild all of the projects in their solution from scratch (i.e. brand new .sln and .vcproj files). It would take me several days to do that, so that is not an option for me. But apparently it can work. My guess: They implicitly did #1 and #2 by taking that approach - only it took way longer than necessary.
A lot of people suggest turning on /VERBOSE in the linker options. In my experience, that rarely helps to do anything but create more confusion. The option exists, so it is probably useful in some cases.