none
SOLVED: C++ calling Managed C++ Dll -> EEFileLoadException in debugger but works correctly if I just run from windows directly. RRS feed

  • Question

  • I have a C++ application usings a DLL written in <Managed C++> that connects to a web service.

    My code is :

    hAuthDll = LoadLibrary("AuthSrvClient_w32.dll");
    authtx = (AuthTransactionType)GetProcAddress(hAuthDll, "AuthTransaction");
    authtx("URL", "UserName", "Password", pData);
    MessageBox(NULL, pData->Response, "HERE", MB_OK);


    Theres also some error checking omitted.

    When I try to run the program thorugh the VS2k5 debugger it always crashes at the authx function call with :

    First-chance exception at 0x7c81eb33 (kernel32.dll) in House_Cpp.exe: Microsoft C++ exception: EEFileLoadException at memory location 0x00129e34..


    The DLL is in the working directory and will the exe file itself.

    Any suggestions?









    My version info is :
    Microsoft Visual Studio 2005
    Version 8.0.50727.42 (RTM.050727-4200)
    Microsoft .NET Framework
    Version 2.0.50727

    Installed Edition: Enterprise

    Microsoft Visual Basic 2005 77642-113-3000004-41818
    Microsoft Visual Basic 2005

    Microsoft Visual C# 2005 77642-113-3000004-41818
    Microsoft Visual C# 2005

    Microsoft Visual C++ 2005 77642-113-3000004-41818
    Microsoft Visual C++ 2005

    Microsoft Visual J# 2005 77642-113-3000004-41818
    Microsoft Visual J# 2005

    Microsoft Visual Studio Tools for Office 77642-113-3000004-41818
    Microsoft Visual Studio Tools for the Microsoft Office System

    Microsoft Visual Web Developer 2005 77642-113-3000004-41818
    Microsoft Visual Web Developer 2005

    Visual Studio 2005 Team Edition for Developers 77642-113-3000004-41818
    Microsoft Visual Studio 2005 Team Edition for Software Developers

    Crystal Reports XI Release 2
    Crystal Reports XI Release 2


    SQL Server Analysis Services
    Microsoft SQL Server Analysis Services Designer
    Version 9.00.2047.00

    SQL Server Integration Services
    Microsoft SQL Server Integration Services Designer
    Version 9.00.1399.00

    SQL Server Reporting Services
    Microsoft SQL Server Reporting Services Designers
    Version 9.00.1399.00
    Thursday, June 22, 2006 1:21 PM

Answers

  • I finally just started with a fresh project and pulled in files  one by one and I once that was done *It worked*.

    Knowing that it was something in the project setting, I ran a diff on the vcproj file and this is where I found the issue.


    ISSUE :

    Somehow the <DEFAULT> value for structure alignment was being set to 1.

    In the GUI projects settings panel the alignment was set to <DEFAULT> but the vcproj file was set to 1.


    I don't know where/why this setting was set to that value nor why it was working as my default value. but this solved the issue.


    Thanks for all the help in tracking this down!
    Friday, June 23, 2006 7:22 PM

All replies

  • One of possible difference between starting an executable from Windows and from Visual Studio is the working directory.

     

    By default, the working directory of executable started from Visual Studio is the directory containing the project file, i.e. your source files.

     

    In order to change the working directory, open project’s properties, go to Debugging --> Working Directory and specify the name of output directory, i.e. Debug. For release build, specify Release.

     

    Now when you start the application from debugger, your program will see the right current directory and should be able to locate your files.

     

    Hope it helps.

    Thursday, June 22, 2006 1:32 PM
  • I've tried that, but failed to mention in the original.

    This one has me frusturated.  Any other settings to look for?
    Thursday, June 22, 2006 1:56 PM
  • I might be missing something but the way you described it, it sounds like AuthServClient_w32.dll is a .NET assembly and contains your C# classes.  Is this correct?  Is AuthTransaction() a static class method?

    Thursday, June 22, 2006 4:23 PM
    Moderator
  • that should be correct.

    The frusturating issue is the same exe will run fine and be able to use the function if I do not run thorough the debugger.


    Thursday, June 22, 2006 5:13 PM
  • Interesting, I didn't know that you could LoadLibrary/GetProcAddress a .NET assembly.  Anyhoo, do you have the DLL both the project's Bin\Debug and Bin\Release folders?  Or in the GAC?

    Thursday, June 22, 2006 5:30 PM
    Moderator
  • Change:

    The DLL is managed C++

    it only have one export the AuthTransaction function

    And the DLL is located in both the release and debug folder as well as the folder I point the debugger to as the Working directory
    Thursday, June 22, 2006 5:46 PM
  • There's an interesting note at the end of this webpage:

    I am discovering that EEFileLoadException ALSO occurs when ANY error occurs in the Managed class - a managed client debug session will yield the proper exception in the Managed class - but when called from the Unmanaged class - blindly, I cannot debug into it - any exception will trigger the EEFileLoadException in the C++ class.


    Thursday, June 22, 2006 6:27 PM
    Moderator
  • Aditional Note:

    I loaded the app from windows directly.  Tried the functionality and it worked.

    Then I simply attached the debugger to the process and it failed at the same function call.

    Its go to be something with the debugger(environment or otherwise) but I can't figure out what.


    Is there some tool that exists to hook into a process to see all the .NET magic going on?

    Thursday, June 22, 2006 8:05 PM
  • I finally just started with a fresh project and pulled in files  one by one and I once that was done *It worked*.

    Knowing that it was something in the project setting, I ran a diff on the vcproj file and this is where I found the issue.


    ISSUE :

    Somehow the <DEFAULT> value for structure alignment was being set to 1.

    In the GUI projects settings panel the alignment was set to <DEFAULT> but the vcproj file was set to 1.


    I don't know where/why this setting was set to that value nor why it was working as my default value. but this solved the issue.


    Thanks for all the help in tracking this down!
    Friday, June 23, 2006 7:22 PM
  • I have the same problem, and pulling files into a new vcproj one by one would take me a week.  It doesn't seem to be a fix for me anyway.

    Struct Alignment was set to default in the property pages of 1) a project that produces a consuming native C++ DLL, 2) the mixed-mode source file that begins using managed modules (in a C++ DLL project with an assembly header), 3) the project which produces a managed only C++ assembly that is used by the mixed-mode file.  I found no references to it being set otherwise by looking at the actual vcproj files.

    Further web search indicated that this error will show up in the event log (and it did):

    ".NET Runtime version 2.0.50727.42 - Fatal Execution Engine Error (79F97075) (80131506)"

    It doesn't explain anything but suggest what the EE stands for.  This sounds like a debugger bug that a handful of people seem to trigger mistakenly or not.  It has already been described here and other places:  a managed exception is thrown someplace in or beyond a mixed managed/unmanaged DLL, which is reached from a native DLL, and the debugger halts.  I tried wrapping parts of code with try/catch blocks, but that will be the next direction from which to attack.  Trying to catch a managed exception before it is rethrown to native-land doesn't seem to work.

    Greg

    Thursday, September 7, 2006 8:51 PM
  • I just took a week (good guess) to go over every project file with a fine toothed comb, and make sure that no struct alignment or basic runtime check options are being set unbeknownst to me.  There were some that probably would cause problems.  There are no FileConfiguration tags in any vcproj file except for the stdafx.cpp file, which only sets the precompiled header setting to "create" (overriding use).  For about half the projects, I even made a new project file from scratch.

    I made sure that the /ASSEMBLYDEBUG flag was set and NOT disabled for all projects.

    I turned off CLR everywhere in all projects except the one purely managed assembly/dll.  I then went to a native-c++ file and typed the following insane lines:

    #using "path/to/managed.dll"

    ......code, code, code.....

    void mynativeclass::mynativemethod(void) {

          managedns::mymanagedclass ^selfLoathing = gcnew managedns::mymanagedclass();

          return;

    }

    This file, and only this file, was then compiled with /clr, and told to use a special precompiled header (which was a verbatim duplicate of the usual stdafx.h, except that it too has been compiled (through stdafx.cpp) with /clr.

    Build the solution, debug it, crash on EEFileLoadException when something calls mynativeclass::mynativemethod

    If I subsititute my the instantiation of my pure-managed class (and corresponding assembly reference) with System::Windows::Forms::MessageBox::Show("Hello-World!"); and then build (not rebuild nor clean-then-build), then I get an enthusiastic message box, and no crash, as expected when debugging.

    Wednesday, September 13, 2006 8:23 PM
  • Just my two bits (I also had this EEFileLoadException in my command-line program calling a MFC-DLL which has one or two managed sources in the project), fixed after almost one day of head-scratching:

    • it seems that the DLL's WinApp-InitInstance member is not called until a call to a function in the managed class which calls a static member function or accesses a static member variable (see http://forums.microsoft.com/MSDN/ShowPost.aspx?PostID=621277&SiteID=1&PageID=0); so, all the initialization that one normally does in InitInstance() is not done until one calls a (dummy) function to force the allocation of managed static memory
    • when I run my command-line program from the debugger, i just get a EEFileLoadException message in the output window; the call stack lines are greyed out (and has only addresses anyway, no function names)
    • when I run (the debug version of) my command-line program from the command window, I get a very long message with stack trace, pre-bind information, ... which seemed to say that my Managed DLL is not signed
    • upon signing the DLL (with the "sn" Post-Build-Event), I got another EEFileLoadException message in the command window saying that one of the dependent DLLs could not be found
    • once these DLLs ware made available, everything worked fine!

    So, what worked for me was:
    1. making the call to a dummy managed function containing something like:
        System::String ^str1 = gcnew System::String("str1");
        System::String ^str2 = gcnew System::String("str2");
        System::String::Compare(str1, str2);
    2. signing the managed MFC-DLL
    3. making sure that all the necessary DLLs are available

    Hope this helps!!

    Edward Clements

     

    Monday, September 18, 2006 2:02 PM
  • Another two bits worth:

    We have an application that needs to call C# from Java.  The call order made is: Java to a native C++/CLI -unmanaged DLL function to a C++/CLI managed function in the same DLL to a C# static method in a class  in another assembly.

    We were getting the EEFileLoadException when the call was made in the C++/CLI managed function to a static method in a class in the C# managed assembly.

    Java doesn't handle C++ exceptions very well, (the JVM will crash) so after a little digging I found that the RuntimeWrappedException class will capture the CLR exceptions for us.  Typically we would have installed an C++ structured exception handler, but this exception class proved adequate.

    See the artricle MSDN article "How to: Catch a non-CLS Exception". 

    After adding a catch for the RuntimeWrappedException exception type, we finally got a more informative message in the Visual Studio Debug output with more helpful information which helped us solve the (obvious) problem:

    LOG: This bind starts in default load context.

    LOG: No application configuration file found.

    LOG: Using machine configuration file from C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\config\machine.config.

    LOG: Publisher policy file is not found.

    LOG: Post-policy reference: MyAssembly, Version=1.0.0.0, Culture=neutral, PublicKeyToken=c81dfdf058223cfb

    LOG: Attempting download of new URL file:///C:/Program Files/Java/jre1.5.0_07/bin/MyAssembly.DLL.

    LOG: Attempting download of new URL file:///C:/Program Files/Java/jre1.5.0_07/bin/MyAssembly/MyAssembly.DLL.

    LOG: Attempting download of new URL file:///C:/Program Files/Java/jre1.5.0_07/bin/MyAssembly.EXE.

    LOG: Attempting download of new URL file:///C:/Program Files/Java/jre1.5.0_07/bin/MyAssembly/MyAssembly.EXE.

     

    Monday, February 12, 2007 5:12 PM
  • Guys, here are two more cents' worth ...

     

    I ran into this problem from a different angle: Interop, where the originator is a COM component calling a method in a .NET assembly.

     

    The .NET assembly ("A") referenced another .NET assembly ("B"). By fluke, I had removed assembly B from the GAC. Attempting to call a method in assembly A caused this error to appear.

     

    What initially confused me was that the method call kept returning a File-Not-Found HRESULT. I was able to load "A", so what was the problem? Argghhh...

     

    Eventually, catching the exception provided a precise error message:

     

      try
      {
         mpAssembly->Method(&param1, etc)   

      }
      catch(_com_error e)
      {
        wchar_t wcstring[1024];
        wcscpy_s(wcstring, (wchar_t *)e.Description());

        // wcstring contains "Could not load file or assembly ..."

      }

     

    Josh

    Wednesday, August 22, 2007 7:56 PM