views:

646

answers:

3

I have some code compiling under the clr and other code that is unmanaged in a single project.

My common.h file includes all the std library headers that I need. It is included by manager.h (forward declaration for manager.cpp (no CLR)), which is included by main_window.h (WinForm) which is included by document_manager.cpp (CLR).

At runtime I get all sorts of weird behavior, in one instance, my form wouldn't load. Pausing the program for debugging several times showed that it was stuck reallocating memory for a std::string, in malloc.c. By changing the code, I can recieve a System::InvalidMemory (I think) exception in ostream.

How do I stop the CLR from managing the std library?

If anyone would like the source to any of my files, just ask.

Edit: In the callstack, I have some managed code that runs when my form loads. In the window init callback, I have a managed to native transition, and then my manager class. Later on, I get to

 std::string error_msg;
 error_msg = "Storage Manager: SQLite Error ("; <-- Executing Currently
 error_msg += sqlite3_errcode(this->db_p);
 error_msg += ") - ";
 error_msg += sqlite3_errmsg(this->db_p);
 *(this->log) << error_msg.c_str() << std::endl;

and the callstack shows std::basic_string::assign, then some other std:: functions, and finally the malloc function, which it is perpetually stuck in.

Edit: The exception that is thrown on file writing:

System.AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
   at manager.file_open(manager* , basic_string<char\,std::char_traits<char>\,std::allocator<char> >* )
   at DocumentManager.main_window.file_open_mainmenu_Click(Object sender, EventArgs e) in c:\development\document manager\document manager\main_window.h:line 456
   at System.Windows.Forms.ToolStripItem.RaiseEvent(Object key, EventArgs e)
   at System.Windows.Forms.ToolStripMenuItem.OnClick(EventArgs e)
   at System.Windows.Forms.ToolStripItem.HandleClick(EventArgs e)
   at System.Windows.Forms.ToolStripItem.HandleMouseUp(MouseEventArgs e)
   at System.Windows.Forms.ToolStripItem.FireEventInteractive(EventArgs e, ToolStripItemEventType met)
   at System.Windows.Forms.ToolStripItem.FireEvent(EventArgs e, ToolStripItemEventType met)
   at System.Windows.Forms.ToolStrip.OnMouseUp(MouseEventArgs mea)
   at System.Windows.Forms.ToolStripDropDown.OnMouseUp(MouseEventArgs mea)
   at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
   at System.Windows.Forms.Control.WndProc(Message& m)
   at System.Windows.Forms.ScrollableControl.WndProc(Message& m)
   at System.Windows.Forms.ToolStrip.WndProc(Message& m)
   at System.Windows.Forms.ToolStripDropDown.WndProc(Message& m)
   at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
   at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
   at System.Windows.Forms.NativeWindow.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
+2  A: 

Have you tried wrapping #pragma unmanaged / #pragma managed around the functions you need to stay unmanaged? While written in a kind of "breathless enthusiasm" tone, http://www.ondotnet.com/pub/a/dotnet/2003/03/03/mcppp2.html does have some tips on mixing managed and unmanaged code/objects.

Alex Martelli
I have tried this, it didn't help.
LM
@LithMaster, combine Alex's suggestion with my answers, that should result in no CLR control over the CPP files you want to run natively.
unforgiven3
A: 

Just a shot in the dark, but try turning off CLR support for the CPP files that you are using STL in. This question shows how to do that for individual CPP files. It effectively compiles them natively.

Fair warning: if you go this route, you may have to turn off precompiled headers the CPP files you compiled natively.

unforgiven3
I already did this before I posted this question. I enabled CLR support for the cpp files, and I got past my problem spot. Now, I'm having trouble with a file that I cannot enable CLR for, sqlite.c. The compiler doesn't let me as it's C, not C++, and compiling it as C++ gives me tons of errors.
LM
Just to clarify, when I ENABLED clr support, that part of my program worked. I get an exception:An unhandled exception of type 'System.AccessViolationException' occurred in Document Manager.exeAdditional information: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
LM
Hmmm, let me think about it - I hope you can get it resolved!
unforgiven3
Some more testing shows that when I get to the error handler shown in my question, I think an exception IS thrown, but it is caught somewhere in the WinForms backend code. If I put a breakpoint on every line in my code in an area where there is an error handler call, the breakpoints after the error handler call do nothing, and the program keeps on going.
LM
+1  A: 

I think you might be hit by the One Definition Rule, from your description. In C++, you are allowed to have multiple definitions for a class, but they should all be identical. This allows you to put class definitions in headers.

You still have to be careful with the "identical" part. This doesn't mean just the tokens in the source code, but their replacement after the prceprocessor and (in practice) the meaning of them given the current compiler settings. A clear example would be the 32/64 bit switch, or the alignment setting - those could change the sizeof of a class.

In your case, you might have two definitions of the Microsofts STL classes, under different settings.

MSalters
I don't fully understand what you mean. I have a single file that includes <fstream>, <string> and all the other STD libraries, and a "#pragma once" at the top of it - is this what you mean?
LM
You're misunderstanding C++ compilation rules. Technically, you don't compile .cpp files. You compile each preprocessor output ("translation unit"). Header files included twice are then part of two different translation units, and the definitions in it are compiled twice - possibly with different settings.
MSalters