I need to debug the release version of my linked library. I am already generating debug information with my release build following this article but how can I do the same with the library project? Note that library project doesn't have link page in properties where debug information is created in the link above. I am using VS2010.
What I really want is to make TRACE work whlile debugging the library. I tried to link debug version of library with the release exe but it creates linker errors.
What I really want is to make TRACE work...
You mean the MFC TRACE macro? The one that writes messages to the debug/output window of the debugger?
Unfortunately, even if you do fix your build settings so that your final executable contains debug information for your static library it won't bring back those trace statements. TRACE is a macro and therefore is handled by the compiler preprocessor. When you compile in release mode, that macro is redefined to be a no-op. It's as if the TRACE statement was deleted from the source code.
Even if you do resolve the problem of adding debug symbols to your library and executable, it won't bring those trace statements back. They were removed during the compile phase.
So what to do? Turns out, if you dig deep enough into those macros, they are ultimately calling a Win32 function OutputDebugString. This call is available in both debug and release versions of the ms libraries. So ... you could replace the trace macros with explicit calls to OutputDebugString - it's not as convenient to code with but at least you will get your debug output in release mode.
BTW, I finally gave up on all those macros years ago and we have completely replaced them with log4cplus calls. Any logging framework would be better than the trace macros - because the time when you really need tracing is not when you are debugging but when your code is in production and you cannot reproduce the problem locally. It's much better to log to a file which the customer can send to you, then rely on tracing that only works in the debugger. Something to consider anyways...
A static library isn't linked, so it's no surprise that linker options are unavailable. You basically just need to tell the compiler to produce debugging information. From there, creating the library is little more than putting a bunch of object files together into a single file.
So basically, just tell the compiler to produce debug information, and the library will contain debug info.
Related
I was working on a MS Visual Studio project and noticed that the Debug build was Linking to a Release library (DLL), when a Debug library with the same name was also available. I switched the path to Link the Debug library, and it seems to still work. Is there any way to know if my change was correct?
Additional Information:
Using the debug DLL triggers a small memory leak that wasn't triggered with the release DLL. Or possibly that is debug related cache data. That leak made me question if it was including the lib headers without _DEBUG somehow. Thus this question.
It is the preferred way to link Debug builds of your program with Debug version of external dynamic libraries as it guarantees that uniform Visual C++ runtime libraries will be used. Mixing libraries built in Debug and Release mode will result in both Debug and Release VC++ runtimes being linked and annoying linker warnings about multiple symbol definitions in conflicting Debug/Runtime libraries.
Sometimes it may be inevitable as i.e. only Release version of some external library may be available. Hence in VC++ there are linker settings allowing to ignore some specific libraries. So you may start checking in the Linker-Input settings of the Debug build if such ignores are already defined for existing conflicts. With some luck you might be able to remove them now.
If using the Debug version of some library breaks the whole program it might be an insight how to improve the whole system, it is that what a Debug build is for anyway.
Assuming that it is the right library (as in the same code compiled to a different configuration), you are right to link to the debug dll on your debug configuration (and should link to the release dll on your release configuration).
The differences tend to be related to the optimisation level (Debug is usually compiled without any optimisation at all) and any symbols that might be included to make it easier to develop with and maybe step into.
Brief introduction:
I am refactoring win32 application, I use VS 2008.
The application consists of both of my own dll and 3-rd party dll`s.
Issue:
When I run the application in the debug mode and execute some action the error is raised: the application programm has triggered a breakpoint, heap is corrupted.
Actions undertaken:
I have searched the internet and found that this error may be because of different build flags (multi-threaded debug /MD and multi-threaded debug dll /MDd) were used for dlls within the project(which results that they use different c runtime libraries, and for each library own list for work with memory is maintained this therfore can lead to the heap corruption).
I have checked my dlls - they all have the same flag: debug multithreaded dll. So I think that one of the 3-rd party DLL maybe was built with multi-threaded debug flag.
Questions:
Is it possible to find out with what flag 3-rd party library was
built, if so how can I do this.
How can I sort you my issue of
different build flags?
Is my guess about that error is due to
different build flags is correct?
Is it possible to find out with what flag 3-rd party library was built, if so how can I do this
Yes. C or C++ DLLs built with Visual Studio versions 2005 and 2008 require a manifest that states what version of the C runtime DLL they need. You can see it with VS, File + Open + File, select the DLL and open the node labeled "RT_MANIFEST". Resource ID 2 is the manifest that states the type and version of the CRT. It should match yours. Export it to make it easier to read. If it is missing then it either wasn't built with /MD or used a completely different version of VS, which in itself is bad news.
How can I sort you my issue of different build flags?
You can't. You'll need to contact the 3rd party and request a build that's compatible with yours.
Is my guess about that error is due to different build flags is correct?
It is possible but not terribly likely. Having a mismatch does not automatically cause a crash, a programmer can certainly design the DLL interface so that's never an issue. You can typically tell from the function signature and documentation. The problem case is where the DLL allocates an object and you are supposed to release it. It will be obvious when the function returns a pointer. Or a standard C++ class library object like std::string. Less obvious is when it throws an exception. Such a problem is also highly repeatable, it will bomb consistently, not occasionally.
The biggest mistake you are making is asking this question here. You should be talking to a programmer employed by that 3rd party that has worked on this DLL. He'll know the exact answer to your questions and can very easily solve your problem. If you cannot get this kind of support then you should not be using these DLLs, they'll make your life miserable for a long time to come.
I was digging around and found an executable for something I wrote in Visual C++ 6.0 about 8 years ago. I never backed up the source code, but I think I always compiled everything in debug mode. I also vaguely remember hearing somewhere that "you can't decompile an executable into source code unless you have your compiler's debugging symbols or something." The code would have sentimental value, but its not mission-critical that I retrieve it.
That's the background; here are the questions:
How do I check if an executable was compiled in debug mode or not?
If it is, what information comes with a debug mode executable?
Can I retrieve full source code? Failing that, can I get any substantial improvement when decompiling compared to a release version? If so, how?
Thanks,
-- Michael Burge
I do not believe there is a flag though you might find something by using PEDUMP which will dump out COFF file formats (Windows EXE and DLLs). You can infer if an executable was compiled for debug rather quickly by running Dependecy Walker and seeing if your EXE is linking to any debug DLLs (suffixed with D, e.g. MSVCRT5D.DLL).
FYI in VC6 Debug and Release are simple named builds, not modes per say, each build a collection of compiler and linker settings. The EXE is just code, debug exes normally not having been optimized which makes using a debugger with it easy (versus debugging optimized code). Thus you can compile a Release binary with Debug Symbols which is sometimes useful for tracking down optimized code errors.
Debug EXEs and DLLs did not contain any debugging information but instead had a sidecar PDB file that resided in the same folder and contains all the debugging symbols information that was produced during compilation.
No, source is source and not compiled into the symbols file or executables. There are some amazing decompilers out there that can regenerate decent C versions of your code but they are amazing only in how good the C is, not in how well they can recreate your source.
With Visual Studio, I am afraid you can't, since the debug executable doesn't contain the source. Visual Studio generates pdb files that only contains the mapping between the binary and the sources filenames and line numbers, but you still need the source code with them. That might be different with gcc, which I think integrate the source itself inside the binaries.
I think that many disassemblers can show the source if a binary is compiled in debug mode. For example, I use OllyDBG and it has an option to show the source, although I've never tried.
I am writing an C++ application that could be compiled under Linux (gcc 4.3) and Windows (MS VS08 Express).
My application uses third-party libraries,
On Linux , they are compiled as shared libraries, while
on Windows, there are two versions "Debug" and "Release".
I know that debug version provides extra support for debugging ( just like using -ggdb option in linux gcc, right? )
But I found that if my application is in debug version , the libraries must also be in debug version, otherwise the application will crash.
Why is there such a limit? It seems that there are no such limits in the linux world
Thank you very much!
The Debug configuration of your
program is compiled with full symbolic
debug information and no optimization.
Optimization complicates debugging,
because the relationship between
source code and generated instructions
is more complex.
The Release configuration of your
program contains no symbolic debug
information and is fully optimized.
Debug information can be generated in
PDB Files (C++) depending on the
compiler options used. Creating PDB
files can be very useful if you later
need to debug your release version.
Debug vs Release
It is also possible to debug your release build with the compiler flags.
Debugging Release Builds
Heap Layout - Guard Bytes to prevent overwriting
Compilation - Removing Assert/Debug Info
Pointer Support - Buffers around pointers to prevent seg faults
Optimization - Inline Functions
Common Problems When Creating Release Builds
To elaborate on Martin Tornwall. The various libraries linked when in Debug or Release
LIBCPMT.LIB, Multithreaded, static link, /MT, _MT
LIBCPMTD.LIB, Multithreaded, static link, /MTd, _DEBUG, _MT
CRT Libraries
Most likely, the Release and Debug versions are linked against different versions of the C++ Runtime library. Usually, a Debug build links against the "Multithreaded Debug DLL" runtime, whereas a Release build will generally link against "Multithreaded DLL". Loading DLLs whose runtime libraries are mismatched with that of the application will often lead to mysterious crashes.
You could try verifying that all your DLLs build against the same runtime library as your application, regardless of which configuration (Debug or Release) is active. Whether or not this is desirable is another question entirely.
The ability to choose which runtime library to link with enables the application developer to select the best feature set given her application's requirements. For example, a single-threaded application might incur performance penalties as a result of unnecessary thread synchronization if it is linked with a runtime library that is designed with thread safety in mind. Likewise, the consequences of linking a multi-threaded application against a single-threaded runtime could potentially be disastrous.
While I never intentionally link libraries that were built with different compiler settings, there isn't much point in doing so, I only know of the STL classes in the Dinkumware implementation (the one MSFT uses) to cause this problem.
They support a feature called 'iterator debugging' which is turned on by default in the Debug configuration. This adds members to the classes to aid the diagnostic code. Making them larger. This goes bad when you create the object in a chunk of code that was compiled with one setting and pass it to code that was compiled with the opposite setting. You can turn this off by setting the _HAS_ITERATOR_DEBUGGING macro to 0. Which is rather a major loss, the feature is excellent to diagnose mistakes in the way you use STL classes.
Passing objects or pointers between different libraries is always a problem if you don't carefully control the compile settings. Mixing and matching the CRT version and flavor gets you in trouble when you do so. This normally generates a warning from the linker, not sure what you did to not see it. There won't be one if the code lives in a DLL.
I have an application I'm working on that uses two third party libraries, each with pre-compiled libs and dlls, one of which provides necessary .lib files for both debug and release builds (A[d].lib) and the other which provides only .lib files for release builds (B.lib).
Compiling in Release mode (using MSVC9) works fine, however attempting to compile in debug mode fails because third party A requires LIBCMTD.lib (or MSVCRTD.lib) while third party B requires LIBCMT.lib (or MSVCRT.lib).
Can I work around this or am I stuck debugging in release mode?
Do you want full debug mode, or do you just want to be able to debug? If the later is the case, just go to the linker options, and turn on the generation of symbolic information (.pdb). This way you can use the debugger in your own code, step through the lines, and look at variables. If you get annoyed by the changes in control flow that the optimizers create, you can go to the compiler options, and turn off optimizations. This way you get to use the debugger AND build in release mode. Once you're happy with your code, you just change the settings back to creating optimized code.
Try passing /NODEFAULTLIB:LIBCMT to the linker.
I am not sure it can be done directly with static libraries. I suggest you package library B into a dynamic library, then use this new B' library. Your problems will have disappeared.