Actually it can be “Could Not Load Type” too, but the reason is the same: you are referencing the wrong DLL version.
well, this is totally understandable; of course you are going to get this exception when you use an outdated DLL that lacks the new extra parameter to THAT certain method. But the interesting part is it will not happen when you first run your application, and neither when execution reaches the changed method; it will happen when code-execution reaches a place that REFERENCES that changed method.
lets look at the following example.
I have created two projects: Windows Forms project called “HostDLL”, and a Class Library project called “BadDLL”.
The HostDLL references the BadDLL; upon clicking a button in the form, the HostDLL will create an instance of class “BadClass” and call the method “DoStuff” which takes two integer parameters.
everything goes fine:
20 private void button1_Click(object sender, EventArgs e)
22 BadClass bc = new BadClass();
23 int x = 3, y = 10;
25 bool never = false;
26 if (never)
28 bc.DoStuff(x, y);
30 MessageBox.Show(“Done successfully”);
Notice the IF clause in line 26, and notice that calling the method “bc.DoStuff” will never take place because the “never” variable is always false.
Now, intentionally, we will make a breaking change in the BadDLL; adding a new integer parameter z to the DoStuff method (we will make this change AFTER we have compiled the HostDLL so we don’t get compile-time correction).
Run the applicaion HostDLL to show the form, you will notice that there is no error, even when the BadDLL has been changed. Now hit the button… you will get a run-time error that says “Method Not Found”. The interesting part of the story is that even though DoStuff will never get called, yet we will still get this run-time error.
The reason is that the JIT compiler does what it’s called after: “Just-In-Time Compiler“; using help from the “CLR via C#” book authored by Jeffery Richter, specifically in “Executing Your Assembly’s Code” section, the explanation is that:
To execute a method, its Intermediate Language must first be converted to native CPU instructions. This is the job of the CLR’s JIT (just-in-time) compiler…Just before the method executes, the CLR detects all of the types that are referenced by the method’s
code (in our case it’s the BadClass). This causes the CLR to allocate an internal data structure that is used to manage access to the referenced types.
The author continues in a graph in which he explains the process:
1. In the assembly that implements the type, look up the method being called in the metadata
2. From the metadata, get the IL for this method
3. Allocate a block of memory
4. Compile the IL into native CPU instructions
So it is at that point the code is compiled, and at that point the JIT discovers that there is a type (which is BadClass in our case) is referenced having an invalid method with one extra parameter.
So always be careful when you reference other DLL’s, if you don’t make sure you have the right version, you will be subject to a potential lovely RTE message