Reflection fails with File Not found.
Hello All:
What's happening; A Net2.0 application loads a custom control using reflection. When the control is actually shown in the interface, the control instantiates another control from the same assembly into another panel of the interface. The User control that is initially instantiated through reflection and is show in the left panel we cal the "SelectControl" and the second user control that is ionstantiated by the "SelectControl" and placed in the Right Panel is called the "ViewControl"
It's a plug-in mechanism we are using. There are already several plugin controls we have built that are used this way in this application that work without issues. so the Architectual model and the code implimentation are working as expected.
Now comes the issue. We are creatring a new plugin that accesses IBM's Websphere MQ series 6.0. When we test these controls in our test frame, instantiating themwithout reflectionthey work without any problems.
In our Production application where the plugin is accessed through reflection, this same plug-in fails when we attempt to show the "View Control" in the right panel. We get the error shown below. The assembly mentioned in the error is a seperate assembly referenced by the plugin assembly. Both the SelectControl and the ViewControl reference the SwitchMQProto assembly references the IBM amqmdnet.dll assembly.
The Select Control is able to access the MQ using the amqmdnet assembly. So it is working through assembly. The ViewControl however, does not instantiate and throws the error below.
Anyone have any experience with this?
===================Error Information==================================
- System.IO.FileNotFoundException {"Could not load file or assembly 'SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null' or one of its dependencies. The system cannot find the file specified.":"SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"} System.IO.FileNotFoundException
+ TargetSite {System.Reflection.RuntimeMethodInfo} System.Reflection.MethodBase
FusionLog "=== Pre-bind state information ===
LOG: User = HTS\ibrahimm
LOG: DisplayName = SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
(Fully-specified)
LOG: Appbase =file:///C:/Documents and Settings/XXXXX/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/
LOG: Initial PrivatePath = NULL
Calling assembly : (Unknown).
===
LOG: This bind starts in default load context.
LOG: Using application configuration file:xxxxxx
\Projects\SwitchAdminConsole\SwitchAdminConsole\bin\Debug\SwitchAdminConsole.vshost.exe.config
LOG: Using machine configuration file from C:\WINNT\Microsoft.NET\Framework\v2.0.50727\config\machine.config.
LOG: Policy not being applied to reference at this time (private, custom, partial, or location-based assembly bind).
LOG: The same bind was seen before, and was failed with hr = 0x80070002.
" String
[3205 byte] By [
IbrahimY] at [2007-12-25]
Where is SwitchMQProto.dll located? Make sure that SwitchMQProto is either in the bin\Debug directory or is registered in the GAC.
Try running fuslogvw.exe. This is a tool provided with the 2.0 (and 1.0 i believe) SDK which helps diagnose all assembly bind failures. It will be located in %ProgramFiles%\Microsoft Visual Studio\SDK\v2.0\Bin. Follow this process
- Start up fuslogvw.exe
- Set it to log all bind failures to disk
- Run your scenario and let it fail
- Switch back to fuslogvw and see if the error message is any more helpful.
Hello:
Ran Fuslogvw
set it to log bind failures to disk
Ran tha application.
Switched back after failure
No log.
I must be doing something wrong :(
In any case, I did get this out of the application's log: (Note the Fusion Log in the error message)
System.IO.FileNotFoundException was unhandled
Message="Could not load file or assembly 'SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null' or one of its dependencies. The system cannot find the file specified."
Source="SwitchESB"
FileName="SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"
FusionLog="=== Pre-bind state information ===\r\nLOG: User = HTS\\ibrahimm\r\nLOG: DisplayName = SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null\n (Fully-specified)\r\nLOG: Appbase = file:///C:/Documents and Settings/IbrahimM/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/\r\nLOG: Initial PrivatePath = NULL\r\nCalling assembly : (Unknown).\r\n===\r\nLOG: This bind starts in default load context.\r\nLOG: Using application configuration file: C:\\Documents and Settings\\IbrahimM\\My Documents\\Visual Studio 2005\\Projects\\SwitchAdminConsole\\SwitchAdminConsole\\bin\\Debug\\SwitchAdminConsole.vshost.exe.config\r\nLOG: Using machine configuration file from C:\\WINNT\\Microsoft.NET\\Framework\\v2.0.50727\\config\\machine.config.\r\nLOG: Policy not being applied to reference at this time (private, custom, partial, or location-based assembly bind).\r\nLOG: The same bind was seen before, and was failed with hr = 0x80070002.\r\n"
Make any sense?
Update on Fuslogvw
I have it working now. Just needed to set a custom path.
Anyway....here is what I get:
*** Assembly Binder Log Entry (10/2/2006 @ 9:58:07 AM) ***
The operation failed.
Bind result: hr = 0x80070002. The system cannot find the file specified.
Assembly manager loaded from: C:\WINNT\Microsoft.NET\Framework\v2.0.50727\mscorwks.dll
Running under executable C:\Documents and Settings\IbrahimM\My Documents\Visual Studio 2005\Projects\SwitchAdminConsole\SwitchAdminConsole\bin\Debug\SwitchAdminConsole.vshost.exe
A detailed error log follows.
=== Pre-bind state information ===
LOG: User = HTS\ibrahimm
LOG: DisplayName = SwitchMQProto, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
(Fully-specified)
LOG: Appbase = file:///C:/Documents and Settings/IbrahimM/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/
LOG: Initial PrivatePath = NULL
LOG: Dynamic Base = NULL
LOG: Cache Base = NULL
LOG: AppName = SwitchAdminConsole.exe
Calling assembly : (Unknown).
===
LOG: This bind starts in default load context.
LOG: Using application configuration file: C:\Documents and Settings\IbrahimM\My Documents\Visual Studio 2005\Projects\SwitchAdminConsole\SwitchAdminConsole\bin\Debug\SwitchAdminConsole.vshost.exe.config
LOG: Using machine configuration file from C:\WINNT\Microsoft.NET\Framework\v2.0.50727\config\machine.config.
LOG: Policy not being applied to reference at this time (private, custom, partial, or location-based assembly bind).
LOG: Attempting download of new URL file:///C:/Documents and Settings/IbrahimM/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/SwitchMQProto.DLL.
LOG: Attempting download of new URL file:///C:/Documents and Settings/IbrahimM/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/SwitchMQProto/SwitchMQProto.DLL.
LOG: Attempting download of new URL file:///C:/Documents and Settings/IbrahimM/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/SwitchMQProto.EXE.
LOG: Attempting download of new URL file:///C:/Documents and Settings/IbrahimM/My Documents/Visual Studio 2005/Projects/SwitchAdminConsole/SwitchAdminConsole/bin/Debug/SwitchMQProto/SwitchMQProto.EXE.
LOG: All probing URLs attempted and failed.
The above referenced assembly is not directly loaded using reflection but is a dependancy being used by another assembly that is being loaded using reflection.I am using the .LoadFromFile() to load the original asssembly.Ibrahim
Sorry, still not 100% clear on what you are doing. Are you calling LoadFromFile to load SwitchMQProto.dll or to load a DLL that is dependent on SwitchMQProto.dll?
Also the output from Fuslogvw lists several paths it tried to load the DLL from. Have you tried putting the DLL into one of those directories and seeing if that fixes the problem?
Hello Jared
>Are you calling LoadFromFile to load SwitchMQProto.dll or to load a DLL that is dependent on SwitchMQProto.dll?
It's a dependancy of a dependancy.
LoadFile loads a usercontrol called QueueManagerSelect. The QueueManagerSelect instantiates another control within the the same assembly. That control is called QueueManagerView.
QueueManagerSelect and QueueManagerView have the dependancy for SwitchMQProto.dll
QueueManagerSelect loads without issues, Connects to the WebsphereMQ and displays data from the Queue.
QueueManagerView fails with the error I am showing you here.
Obviously, when the QueueManagerSelect control is loaded, SwitchMQProto.dll is being found and loaded as well.
There is no direct call in code to load QueueManagerView. It is loaded as a dependancy to QueueManagerSelect.
Ibrahim
How about the second part, have you put the DLL in the paths that FusLogVw reported it looked for it at?
Jared
Move the DLL into one of the paths.
Yes, it loaded as it should load.
This is not an optimal solution though. This dll should load from the path that the plugins are loaded from. Please tell me there is a cure 
And buy the way, thank you for this great support!
Ibrahim
This behavior is unfortunately by design. By default .Net will load DLL's only from the following locations
- GAC
- Directory containing the executable
- Sub Directory of the executable specified in the configuration file
So even though the failing DLL is in the same directory is the Plugin the framework assembly loader will not find this DLL. There are 3 work arounds
- Put the DLL into your application's directory
- Put the DLL into the GAC
- Have the plugin specifically load the DLL from it's directory if it's not already loaded (via LoadFrom)
Is this for real? I'm trying to upgrade an application from .NET 1.1 to .NET 2.0. The application is an Excel add-in that has a main entry assembly and supporting satellite DLLs which work perfectly under .NET 1.1. The add-in includes 3rd party UI assemblies so there is no concept of "put them all in a single assembly". Nor is it practical to install the assemblies into sub-folders of Excel on client machines. Nor is it an option to add a config file to the Office folder so that a private path can be added. You can imagine the WTF reaction from IT admins if either of these options is proposed.
The add-in fails to load when Excel starts for all the reasons listed in this thread. Surely the use of .NET to create multi-assembly Excel add-ins is not an unusual use case for .NET. However, if I follow the thread correctly and have interpreted your last comment correctly, the conclusion is that in the transition from .NET 1.1 to .NET 2.0 a backwards incompatible change has been made that prevents .NET being used in a fairly normal scenario. Have I mis-interpreted something?
Bill Seddon
Hello Bill;
Yes it is for real 
Putting them in the GAC is not so bad. But you'll have to strong name them
Ibrahim