views:

483

answers:

4

Hi,

I'm trying to create a splash screen that shows assemblies (all referenced library) loading status. I use AppDomain.AssemblyLoad AssemblyLoadEventHandler delegate to catch what assembly is being loaded but the problem is the event is not triggered when the program initializes. I tried register the event handler in application startup "MyApplication_Startup" but it didn't work. Here's my test code:

    Partial Friend Class MyApplication

    Private Sub MyApplication_Startup(ByVal sender As Object, ByVal e As Microsoft.VisualBasic.ApplicationServices.StartupEventArgs) Handles Me.Startup
        AddHandler AppDomain.CurrentDomain.AssemblyLoad, AddressOf MyAssemblyLoadEventHandler
    End Sub

    Sub MyAssemblyLoadEventHandler(ByVal sender As Object, ByVal args As AssemblyLoadEventArgs)
        Console.WriteLine(">>> ASSEMBLY LOADED: " + args.LoadedAssembly.FullName)
        Console.WriteLine()
    End Sub

End Class
A: 

Hmm I'm not sure about the VB syntax, but in C#, I would put it in the Program's Main(...):

static void Main(string[] args)
{
    AppDomain.CurrentDomain.AssemblyLoad += new AssemblyLoadEventHandler(CurrentDomain_AssemblyLoad);
}

static void CurrentDomain_AssemblyLoad(object sender, AssemblyLoadEventArgs args)
{
    Console.WriteLine("Loaded " + args.LoadedAssembly.FullName);
}

UPDATE: Using Reflector, the VB syntax seems to be:

Private Shared Sub Main(ByVal args As String())
    AddHandler AppDomain.CurrentDomain.AssemblyLoad, New AssemblyLoadEventHandler(AddressOf Program.CurrentDomain_AssemblyLoad)
End Sub

Private Shared Sub CurrentDomain_AssemblyLoad(ByVal sender As Object, ByVal args As AssemblyLoadEventArgs)
    Console.WriteLine(("Loaded " & args.LoadedAssembly.FullName))
End Sub
Michael Bray
A: 

I did try this one before but it didn't work. Did it work in your project?

A: 

The problem is that a lot of the assemblies (well, all of them) are already loaded by the time Main() starts running. To verify that, set a breakpoint on your Startup event handler. When it breaks, use Debug + Windows + Modules to see what is loaded.

Hans Passant
+1  A: 

One issue you are going to run into is that assemblies in .Net are not loaded until they are needed.

For instance, create a new assembly with a "Hello World" class in it, reference it with any executable, then delete the new assembly from the working directory, at no time will you notice that it is loaded.

Next, on a button click event, initialize the "Hello World" class, keep the assembly deleted from the working directory, and you will receive the error that the assembly can not be found when the button is clicked.

This is the key reason that first database access is generally slow in .Net, and has a "speed up" feel to it (more you use it, the faster it gets), that is because the objects you use in your data layer are not loaded into the runtime until they are accessed.

Tom Anderson
One "fix" for the loading problem is to have a method that creates instances of types found in the various assemblies you need to load. Calling the method will then force the assemblies to be loaded.
Rune Grimstad