3

I have a native C++ dll which I call from a managed c++ dll which is called from a C# application.

The function in the native dll looks something like this:

std::string NativeClass::Test()
{
    return std::string("some string");
}

The managed C++ function that calls it looks something like this

String ^ ManagedClass::Test()
{
    std::string temp = this->_native->Test();
    String^ sRet = msclr::interop::marshal_as<String^>(temp);

    return sRet; // crashes here !!!
}

However, on executing the return statement, the application crashes with an error like

Debug Assertion Failed!
debug_heap.cpp
Line 980
Expression: __acrt_first_block == header

I looked all over Stackoverflow but I've not solved it yet. Any ideas?

TimR75
  • 379
  • 2
  • 13
  • What happens if you try to use either of the strings before the return statement? Could you add a printf of the unmanaged string and a Debug.WriteLine of the managed string, and let us know what happens? – David Yaw Aug 25 '16 at 15:49
  • the unmanaged string write out "some string" and the managed string writes out "some string" – TimR75 Aug 25 '16 at 15:57
  • 4
    Standard C++ library types like std::string often misbehave badly like that when they get allocated in one DLL and destroyed in another. It is crucial that the exact same version of the CRT is used to create and destroy the object. Be sure to rebuild that native DLL with the exact same version of the compiler using the exact same settings (minus /clr), /MD is required. – Hans Passant Aug 25 '16 at 15:57
  • @Tim49 Try to marshal `std::string` via `String^ sRet = gcnew String(temp.c_str());`. This is the other approach suggested at [MSDN](https://msdn.microsoft.com/en-us/library/ms235219.aspx). – Nikita Aug 25 '16 at 16:38
  • If both string objects are valid inside the `ManagedClass::Test` method, then I think it's not the marshalling or the cross-DLL thing. What can you tell us about where you're calling `ManagedClass::Test` from? – David Yaw Aug 25 '16 at 17:07
  • @Nikita that's what the `marshal_as` specialization does – Lucas Trzesniewski Aug 25 '16 at 17:24
  • 3
    Don't focus on the marshaling, that is not what failed. It was the std::string destructor that bombed. The *temp* object gets destroyed at the end of its scope block, makes it look like it is return statement that fell over. – Hans Passant Aug 25 '16 at 17:57
  • Seems ["Debug Assertion Failed! ... __acrt_first_block == header"](http://stackoverflow.com/questions/35310117/debug-assertion-failed-expression-acrt-first-block-header) article related to the problem. Try to check compiler settings as @HansPassant suggested. – Nikita Aug 25 '16 at 18:02
  • Hans helped solved this. It was indeed a mismatch between the CRT versions in the native dll and managed dll. I was sure I had already checked this but obviously missed it. The code otherwise works as is. Thanks. – TimR75 Aug 26 '16 at 10:10

1 Answers1

1

Hans helped solved this. It was indeed a mismatch between the CRT versions in the native dll and managed dll. I was sure I had already checked this but obviously missed it. The code otherwise works as is. Thanks.

TimR75
  • 379
  • 2
  • 13