tags:

views:

991

answers:

3

Heres my problem:

I have 2 projects - one 'common' projects with acts like a library with all kinds of support code, and the actual program that uses said project in many of its calls. We'll call these projects "Common" and "Program". They are both in the same solution.

Within "Common", I have a class for commo reflection tasks, like creating an instance. If I call GetExecutingAssembly, it gets all the "Common" Types, however when I use GetEntryAssembly I get the "Program" types.

While I certainly could edit the code to work with 2 sets of asm, I'm afraid of a situation where there are more than just 2 projects in the solution - lets say 5 (don't know why, but lets just go there for now), and I'm afraid that calling GetExecutingAssembly and GetEntryAssembly will not get all the Types in the entire program.

Is there something else that i can do to get all the Types in a solution?

+6  A: 
Assembly[] assemblies = AppDomain.CurrentDomain.GetAssemblies();

This will get all of the loaded assemblies in the current AppDomain.

As noted in the comments, it's possible to spawn multiple AppDomains, in which case each can have its own assemblies. The immediate advantage to doing so is that you can unload Assemblies by unloading the containing AppDomain.

pyrochild
May or may not work subject to 1) if the app spawns multiple AppDomains 2) if all ref assemblies have been loaded before this point
Gishu
Perfect, thanks!
cyberconte
@Gishu: "if all ref assemblies have been loaded before this point" Not quite sure what you mean by that. Can you elaborate?
pyrochild
Correct me if I'm wrong: The CLR won't load a referenced assemblies (even modules within a single assembly) until it is needed. E.g. So RefAsmA would be loaded only when the code in the entry assembly makes a reference to a type defined in RefAsmA - calls a static method or creates a type defined in it. At that point the assembly is loaded into the loader heap of the current AppDomain.
Gishu
Ah, yes, you're right.
pyrochild
+2  A: 

How about GetReferencedAssemblies to work off the AssemblyRef metadata entries? The 'solution' is not something that the CLR knows or cares about.. it deals in Assemblies.

private static List<Assembly> GetListOfEntryAssemblyWithReferences()
{
  List<Assembly> listOfAssemblies = new List<Assembly>();
  var mainAsm = Assembly.GetEntryAssembly();
  listOfAssemblies.Add(mainAsm);

  foreach (var refAsmName in mainAsm.GetReferencedAssemblies())
  {
    listOfAssemblies.Add(Assembly.Load(refAsmName));
  }
  return listOfAssemblies;
}

Caveats:
1. You still need to filter core assemblies System.* 2. This just goes one level deep in the ref chain.. but can be done recursively - with more code.

Gishu
+2  A: 

Also: Some assemblies are not loaded straight away, so you should also put an Event Handler on the AppDomain's assembly load event.

AppDomain.CurrentDomain.AssemblyLoad += ....
Tim Jarvis