I have the following three projects in my solution:
1. C# library
2. C++/CLI managed code
3. C++ unmanaged code
I did check "Enable Unmanaged Code Debugging" in my C# project, and built both C++ projects in Debug/Win32. However, I cannot step into unmanaged code - when I F11 on the call of any unmanaged method, it shows me some random/wrong code then exits.
Because my unit tests pass, I know that my unmanaged code does execute.
What am I missing?
When I've had this problem it has come from one of these things:
1) Enable unmanaged code debugging not checked. You already fixed this.
2) Built the EXE as x64 or Any CPU (they say x64 works, but it doesn't). I think you already fixed this.
3) "Just my code" being turned on sometimes causes trouble with unmanaged code debugging (Tools, Options, Debugger, Just My Code)
4) Incorrect debug options in the C++ project settings
5) Missing, corrupted or mismatched PDB files. You can check for this by trying to set a breakpoint in your C++ code while running in the debugger. If the breakpoint turns into a hollow circle, something is wrong with your debug info. Also check your output window as you run in debug mode -- it should tell you whose symbols got loaded.
I've seen this issue going the "other" way from time to time (ie, from native C++ to C++/CLI) and it's usually caused by the debugger not really picking up that it's supposed to debug both native and managed code.
Usually for me, setting the Debugger Type in Configuration Properties -> Debugging in your startup project from 'Auto' to 'Mixed' solves the problem.
Related
I have a severe problem with mixed debugging in MSVC2013. After a call to a COM method from a native C++ DLL, debugger does not stop at breakpoints any more.
Code structure
The picture above presents the overall structure of the code.
I have a single solution with about ten C# projects, about fifty C++ native projects, and one C++/CLI project serving as a bridge between managed and native worlds. Startup project is a C# WPF project (GUI Application), it calls C++/cli project (Bridge) internally, which in turn calls various native C++ Dlls (Various libraries). Alternatively, I can make a C++ console application (Service console app) as startup project for testing purposes only.
I have implemented a library to import some information from Autodesk Inventor document files. Inventor Apprentice COM server (Inventor Apprentice on picture) is used to achieve it, which was freely downloaded alongside with Inventor View 2015. As a first step, the import was implemented in a standalone native C++ console application, and everything worked fine. Then it was adapted to be used in the whole infrastructure as a native C++ dll (Import library), and the debugging hell started.
Symptoms
"debugging broken". In a debug build, after calling the following COM method in Import library:
auto pComponentDefinitions = pDocument->GetComponentDefinitions();
breakpoints in C++ code are no longer hit. Even if I set a breakpoint in the code of another DLL, it is not hit. Breakpoints still visualize as full red circles, so this is not related to PDB issues.
The application itself continues to execute, and some time later I can see the correct results of data import visible in GUI, meaning that Import library has executed correctly. After that, I can pause the GUI Application with Break All button, in which case the main thread is shown stuck deeply inside one of the Inventor's dlls (rse.dll), which cannot be true because that thread has finished import and has even returned correct results.
In the Output window, I can see the following messages, appearing during the problematic COM method call (access violations seem to be normal in Apprentice):
First-chance exception at 0x000007FEDD451F0C (rse.dll) in GUIApplication.exe: 0xC0000005: Access violation writing location 0x000007FFFDE3AFCC.
The Common Language Runtime cannot stop at this exception. Common causes include: incorrect COM interop marshalling and memory corruption. To investigate further use native-only debugging.
First-chance exception at 0x000007FEDD455F6C (rse.dll) in GUIApplication.exe: 0xC0000005: Access violation writing location 0x000007FFFDE3EE6C.
I have tried to embed breakpoints into the code at the moment of compilation, by inserting __debugbreak() before and after the problematic import code. The first one is hit (if debugging is not yet broken), but the second one is not. On the other hand, debugger clearly notices it, because it writes the following message to Output window:
The process hit a breakpoint the Common Language Runtime cannot continue from.
This may be caused by an embedded breakpoint in the native runtime or a breakpoint set in a can't-stop region.
To investigate further, use native-only debugging.
Google gives no results at all for this diagnostic message. It sounds like MSVC thinks it is debugging managed code, which is actually native.
"crashes in call". In case of release build, running the application in mixed debugging mode results in a crash inside rse.dll during the problematic COM call.
Reproducibility
I use MSVC 2013 update 4. Project is built in x64 mode. Net Framework v4.0 is used. Inventor Apprentice from Inventor 2015 is used.
Experimentation shows that:
Everything is OK when no debugger is attached.
Everything works correctly (including debugging), when native-only debugging is used (either via Service console app or after attaching to already running process in native only mode).
In mixed (i.e. native + managed) debugging mode the problem reproduces regardless of whether GUI application was started with debugging or debugger was attached to a working process.
There is a problem both in debug and release modes, but it acts differently. In debug build crazy debugging issues arise ("debugging broken"), but in release it simply crashes somewhere inside ("crashes inside").
Full list of runs performed can be seen here.
The main question
Has anyone seen similar behavior before? What may be the cause of such behavior? Is there a way to fix it?
Disabling the new managed debugging engine of MSVC has helped to fix the issue. It can be done by going to Tools > Options > Debugging > General > tick "Use Managed Compatibility Mode".
While trying to find a workaround for the issue, I have posted the following question. Hans Passant has posted not only a workaround, but also a solution to my main problem. It seems that new debugging engine is not properly working in case of C++/CLI interop.
P.S. Given that the symptoms are quite unique and crazy, I decided to post the full question with the answer, hoping that this information may help some people with similar problems in future.
I wonder if there is any way to debug c++ dll called from C# PInvoke in VS 2010. I tried to attach the project into c# application but it didn't work - didn't stop at a break point.
I also tried to record anything with OutputDebugString in C++ project but nothing printed with PInvoke call. Despite these issues, the actual function runs well.
Any advice will be appreciated.
Both require turning on the same option: Project > Properties > Debug tab > tick the "Enable unmanaged code debugging" option.
You can now set a breakpoint in the native DLL code, it will turn from hollow to solid as soon as the C# project loads the DLL. And OutputDebugString() output will go to the Output window thanks to the unmanaged debugging engine being used.
If you run up a C++ debugger while your program is running, and then go to Debug->Attach To Process->Find your process and attach to it. You should be able to debug it.
Make sure that you have compiled your DLL with the debugger symbols. (.pdb) file and that they are in the directory where you run things from.
When attaching, change the "Attach to" value to "Native". The process should not be running under the managed code debugger - instead of "Debug", use the "Run" command to start.
Also, the DLL needs to be compiled with debug info for any sensible debugging to take place. Make sure you're not P/Invoking the Release build.
The OutputDebugString() should work regardless of debugging mode, however.
I've got a C# DLL with native exports, which is called from some Delphi 2009 code. The Delphi code uses LoadLibrary and GetProcAddress to access the exported functions. I'd like to debug the managed part of the code at runtime, but I'm running into trouble.
When I launch the application, the breakpoints appear properly, but fail to be hit.
My current setup is the following:
C# DLL project in Visual Studio 2010
Project's debug settings set to "Start external program", pointing at the Delphi executable.
Enabled unmanaged code debugging is switched off.
Just My Code is enabled in the debug options (this seems to make no difference)
I've tried enabling unmanaged code debugging, but that causes an error saying "binary was built without debug information". If I continue, all breakpoints are disabled.
When I checked the modules list, the executable shows as having no debug symbols. Delphi doesn't generate a PDB (it can't, since it's a closed-spec proprietary format) but it generates a MAP file instead. I had a look around for MAP-to-PDB converter tools, but it seems there's only a tool for doing the reverse of what I need.
I'm not really interested in debugging the Delphi code from Visual Studio, since I can already do that in the CodeGear Delphi IDE, but is there a way to debug the managed code at runtime in this situation?
Ok, I found a solution. The issue wasn't with debug symbols, but rather the type of code being debugged. If you launch an application from your project startup settings, the debugger starts in mixed mode, which requires native symbols to be available in order to catch C# code invoked from native code.
I wasn't able to get Visual Studio to accept the pdb files created by tds2dbg, so I found a workaround. In order to ensure that the debugger launches in managed mode, attach to the process instead of launching it, like so:
Debug -> Attach to process...
Select the running process.
Click the "Select..." button to the right of "Attach to".
Select "Debug these code types"
Check Managed (v2.0, v1.1, v1.0) for .NET 3.5 or less, or Managed (v4.0) for .NET 4.0 or later. Not sure why v3.5 is excluded from the naming here.
Click OK, click Attach.
After this, all breakpoints should work nicely :)
There is a "tds2pdb" you can try to create a .pdb file:
http://code.google.com/p/map2dbg/downloads/detail?name=tds2pdb102.zip
Note: it's not a complete .pdb file (specs aren't available) but at least it is working for stack traces. However, not all symbols (classes, variables, parameters) are exported. But you can always try...
My main startup project is in c++. the solution involves also managed c# code.
When I debug - I have breakpoints only on the unmanaged sections (on managed breakpoint it states : "The breakpoint will not currently be hit. invalid file line "
I checked the reference and saw that there is dll and pdb there.
What could it be?
how to set mixed-mode debugging
http://msdn.microsoft.com/en-us/library/kbaht4dh(v=vs.100).aspx
And don't miss the link in the bottom.
If, like me, you are trying to debug a C++/CLI from a native C++ project (i.e. you've set /CLR on a single file), and it never hits breakpoints and can't be stepped into. Well my friends, in VS2015 go to
Tools->Options->Debugging->General
and tick the little box that says:
Enable .NET Framework source stepping
I believe you also need to set it to mixed-mode debugging ala the answers above, but that alone was not enough for me. With that box ticked I can go "step into" from my unmanaged C++ into managed code... there is a crazy amount of technology going on under the hood here...
You have to enable mixed-mode debugging. I can't recall where that is, offhand.
I have had many issues with mixed mode debugging. Indeed, some programs get instable (Excel interop mainly for me), and you cannot Edit and Continue any more.
One good way to debug managed and unmanaged mode at the same time is to setup a new dummy project, which will attach a unmanaged debugger to your application. You can debug the managed code with your old project, detach it and attach the native debugger when you want to debug the native code. This way, you also have edit and continue for both codes.
Instructions on setting this up are there.
I am writing a Windows CE application in C# that references a native C++ DLL (that I am also coding) using the following method:
[DllImport("CImg_IP_CE.dll")]
public static unsafe extern void doBlur(byte* imgData, int sigma);
This actually works fine but I am unable to debug the DLL. When I check the debug modules that are loaded after running the EXE, CImg_IP_CE.dll is not one of them. Even after calling functions successfully from the DLL it still does not show up in the modules list.
Upon looking around, it seems that the LoadLibrary() function might work, but I cannot find any examples of using this in a C# Windows CE application. How would I do this or is there a better way to make sure the DLL loads up for debugging?
I found the answer through this post:
http://www.eggheadcafe.com/conversation.aspx?messageid=31762078&threadid=31762074
In summary, the same question was asked and the response was:
No, you can't step from managed code through a P/Invoke call into native
code in the Smart Device debugger. You might be able to use Attach to
Process to do the native debugging (with the native DLL project loaded into
that instance of VS2005), or simply write debug information from the native
DLL to a serial port or something. This really doesn't come up very often,
though, where you actually need to step from one to the other.
Further along in the thread, someone figured out how to accomplish this:
A quick test shows that the easiest way to handle this is to 'run' your DLL.
That is, set the debugging options to start the managed code EXE that will
use your DLL and set your breakpoints in the DLL (all from the DLL project,
of course). Naturally, when the EXE starts, your DLL won't be loaded, so
you'll see the breakpoints as hollow circles with ! on them, but, when you
call any of the native functions in your DLL, the DLL will be loaded (it's
not loaded on startup), and the breakpoints will be set.
So strangely, when you run the C# program and make a call to the native DLL code, it still does not show as loaded in the debug modules window. However, if you set the DLL project as the startup project, and then set the Remote Executable as the EXE file in the Debugging options, now when you first call the DLL, it will load up in the debugger. Okay... whatever works!
Unfortunately, it seems that WinCE mixed mode debugging is not supported. That is, you can debug your process either as managed (so you can step through and set breakpoints in your C# code), or as native (so you can do the same for native code, including this DLL), but not both at the same time.
To run debugging in native mode on a C# project, you can do this: start application without debugging (Ctrl+F5 or Debug -> Start Without Debugging), then Debug -> Attach to Process, set "Transport" to "Smart Device", select the emulator from the "Qualifier" dropdown, click on "Select" button on the "Attach to" field, and check "Native". You will observe that it won't let you check both at the same time, but if you only need to debug the DLL, it may be sufficient...
If you are able to call the function in the DLL without it throwing an application, you are most likely loading the DLL. You may need to make sure that unmaanged debugging is enabled in your project properties though.
Unable to set breakpoints in C DLL used by C++/CLI called from C#