|
dev
newsgroups
|
|||||||||||||||||||||||
|
|||||||||||||||||||||||
Proper unmanaged to managed exception handling -- SEHException andfrom unmanaged code. Specifically, I've got a legacy MFC based DLL that's wrapped by C++/clr exposing it to a fairly straight forward C# console app (VisualStudio 2005 if that matters). According to a fairly brief comment in the documentation for SEHException: "the SEHException class does not cause unmanaged C++ exception destructors be called. To ensure that unmanaged C++ exception destructors are called, use the following syntax in the catch block."[1] The example C++ code shows a catch(...){} clause being used. What I've found is that the recommended construct has *no effect* on the execution of unmanaged C++ exception destructors. They will infact be called as the exception goes out of scope just like it's supposed to. With one exception... The auto delete functionality of MFC based CException is not provided for. In my mind, this really has nothing to do with managed vs unmanaged code since plain old C++ exceptions won't provide for CException auto deletion unless you use the godaweful TRY, CATCH, and CATCH_ALL macros or call the exceptions Delete() member explicitly. This is just how you're supposed to use MFC exceptions. BTW, according to the Exception Handling in MFC documentation: "If you're writing a new application using MFC, you should use the C++ mechanism. You can use the macro-based mechanism if your existing application already uses that mechanism extensively."[2] I have verified that the default CException to SEHException conversion mechanism does *not* call the exception's Delete() member. I think this is a bug in the CLR, but I'm not sure where to post it. Any thoughts or comments? It sounds like the only correct way to handle calling from managed to unmanaged code is: 1) Guarantee the invoked unmanaged code will *never* generate an MFC exception. Or, 2) Wrap every call into unmanaged MFC code with the following: try { // Call unmanaged code } catch (CException* e) { // Pull any info you need from the exception. e->Delete(); throw UserDefinedOrSEHException(); } What am I missing since that looks pretty darn gross? [1] http://msdn2.microsoft.com/en-us/library/system.runtime.interopservices.sehexception.aspx [2] http://msdn2.microsoft.com/en-us/library/t078xe4f.aspx -- Mark Moore (408) 489-4272 liame: moc.detimil***@eroom.kram Mark Moore wrote:
Show quote > It sounds like the only correct way to handle calling from managed to I think you've accurately summed up the situation. It would be nice if the > unmanaged code is: > > 1) Guarantee the invoked unmanaged code will *never* generate an MFC > exception. Or, > 2) Wrap every call into unmanaged MFC code with the following: > > try > { > // Call unmanaged code > } > catch (CException* e) > { > // Pull any info you need from the exception. > e->Delete(); > throw UserDefinedOrSEHException(); > } > > What am I missing since that looks pretty darn gross? default CLR behavior was to call the CException::Delete member when it catches a CException* - you might want to put that in as a suggestion/bug report at http://connect.microsoft.com/feedback/default.aspx?SiteID=210 -cd Carl,
I checked out the link, but unless I'm missing something, I didn't see a way to leave feedback. I could only search the feedback forum for this issue. (It hasn't been entered.) Since you seem to be familiar with the feedback forum, can you either post the issue, or give me some pointers on how I might be able to? Thanks either way for the quick response. -- Show quoteMark Moore (408) 489-4272 liame: moc.detimil***@eroom.kram "Carl Daniel [VC++ MVP]" wrote: > Mark Moore wrote: > > It sounds like the only correct way to handle calling from managed to > > unmanaged code is: > > > > 1) Guarantee the invoked unmanaged code will *never* generate an MFC > > exception. Or, > > 2) Wrap every call into unmanaged MFC code with the following: > > > > try > > { > > // Call unmanaged code > > } > > catch (CException* e) > > { > > // Pull any info you need from the exception. > > e->Delete(); > > throw UserDefinedOrSEHException(); > > } > > > > What am I missing since that looks pretty darn gross? > > I think you've accurately summed up the situation. It would be nice if the > default CLR behavior was to call the CException::Delete member when it > catches a CException* - you might want to put that in as a suggestion/bug > report at > > http://connect.microsoft.com/feedback/default.aspx?SiteID=210 > > -cd > > > Mark Moore wrote:
> Carl, It's rather silly.> > I checked out the link, but unless I'm missing something, I didn't > see a way to leave feedback. I could only search the feedback forum > for this issue. (It hasn't been entered.) > > Since you seem to be familiar with the feedback forum, can you either > post the issue, or give me some pointers on how I might be able to? On the front page, click "Submit Feedback" On the search page, type in something to search for. On the search results page, click "Submit Feedback" On the next page, click "bug submission form" or "Suggestion submission form" Type in your info and submit. If you post the URL to your feedback here on the newsgroup, other people who follow this thread will be able to find it a vote on it. -cd |
|||||||||||||||||||||||