Thank you all for the help.
I found the solution for the problem I was facing. Here is the complete code for what I was trying to achieve.
The AppDomain to which the assembly is loaded tries to resolve the assembly references for the referenced assemblies automatically. If the referenced assemblies are in the same directory as that of application or if it is in GAC then assembly resolution succeeds. In case it is unable to resolve then "AssemblyResolve" event is fired. By subscribing to this event we can attempt resolving the references.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Reflection;
namespace AssemblyInformation
{
public partial class Form1 : Form
{
BindingFlags bindingAttributes = BindingFlags.Public | BindingFlags.Instance;
BackgroundWorker workerThread;
StringBuilder stringBuilder = new StringBuilder();
public Form1()
{
InitializeComponent();
workerThread = new BackgroundWorker();
workerThread.DoWork += new DoWorkEventHandler(workerThread_DoWork);
workerThread.ProgressChanged += new ProgressChangedEventHandler(workerThread_ProgressChanged);
workerThread.RunWorkerCompleted += new RunWorkerCompletedEventHandler(workerThread_RunWorkerCompleted);
workerThread.WorkerSupportsCancellation = true;
}
void workerThread_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
ResultsTextBox.Text = stringBuilder.ToString();
}
void workerThread_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
}
void workerThread_DoWork(object sender, DoWorkEventArgs e)
{
IList<string> fileNames = e.Argument as IList<string>;
ProcessAssemblies(fileNames);
}
private void WordWrapCheckBox_CheckedChanged(object sender, EventArgs e)
{
ResultsTextBox.WordWrap = WordWrapCheckBox.Checked;
WordWrapCheckBox.Font = new Font(WordWrapCheckBox.Font, WordWrapCheckBox.Checked ? FontStyle.Bold : FontStyle.Regular);
}
private void AttributesCheckBox_CheckedChanged(object sender, EventArgs e)
{
CheckBox attributeCheckBox = sender as CheckBox;
if (attributeCheckBox != null)
{
attributeCheckBox.Font = new Font(attributeCheckBox.Font, attributeCheckBox.Checked ? FontStyle.Bold : FontStyle.Regular);
}
}
private void BrowseButton_Click(object sender, EventArgs e)
{
if (AssemblyOpenFileDialog.ShowDialog() == System.Windows.Forms.DialogResult.OK)
{
ResultsTextBox.Clear();
SelectedAssemblyTextBox.Text = AssemblyOpenFileDialog.SafeFileNames.GetCommaSeperatedValue();
workerThread.RunWorkerAsync(AssemblyOpenFileDialog.FileNames);
}
}
private void ProcessAssemblies(IList<string> assemblyNames)
{
try
{
string assemblyName = string.Empty;
this.BeginInvoke((Action)(() => this.Cursor = Cursors.WaitCursor));
AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(appDomain_AssemblyResolve);
for (int i = 0; i < assemblyNames.Count; i++)
{
assemblyName = assemblyNames[i];
if (File.Exists(assemblyNames[i]))
{
string path = Path.GetDirectoryName(assemblyName);
Directory.SetCurrentDirectory(path);
stringBuilder.Append(assemblyName + Environment.NewLine);
stringBuilder.Append("---------------------------------" + Environment.NewLine);
Assembly assembly = Assembly.LoadFile(assemblyName);
AppDomain.CurrentDomain.Load(assembly.GetName());
IList<assemblyname> referencedAssemblyNames = assembly.GetReferencedAssemblies();
foreach (AssemblyName assemblyNameRef in referencedAssemblyNames)
{
try
{
AppDomain.CurrentDomain.Load(assemblyNameRef);
}
catch (FileNotFoundException)
{
string referencedAssemblyPath = path + "\\" + assemblyNameRef.Name + ".dll";
AppDomain.CurrentDomain.Load(referencedAssemblyPath);
}
}
PrintAllPublicMembers(assembly);
}
}
}
finally
{
this.BeginInvoke((Action)(() => this.Cursor = Cursors.Default));
}
}
Assembly appDomain_AssemblyResolve(object sender, ResolveEventArgs args)
{
string path = Path.GetDirectoryName(AssemblyOpenFileDialog.FileName) + "\\" + args.Name.Substring(0, args.Name.IndexOf(",")) + ".dll";
Assembly MyAssembly = null;
if (File.Exists(path))
MyAssembly = Assembly.LoadFrom(path);
else
{
this.Invoke((Action)(() =>
{
OpenFileDialog resolveAssemblyFileDialog = new OpenFileDialog();
resolveAssemblyFileDialog.FileName = args.Name.Substring(0, args.Name.IndexOf(",")) + ".dll";
resolveAssemblyFileDialog.Filter = resolveAssemblyFileDialog.FileName + "|" + resolveAssemblyFileDialog.FileName;
resolveAssemblyFileDialog.Multiselect = false;
if (resolveAssemblyFileDialog.ShowDialog() == System.Windows.Forms.DialogResult.OK)
{
MyAssembly = Assembly.LoadFrom(resolveAssemblyFileDialog.FileName);
}
else
{
DialogResult appClosureConfirmationDialogResult = MessageBox.Show("Unable to proceed without resolving reference to the '" + args.Name + "' assembly. Do you want to try again?", "Assembly Information", MessageBoxButtons.YesNo, MessageBoxIcon.Error, MessageBoxDefaultButton.Button2);
if (appClosureConfirmationDialogResult == System.Windows.Forms.DialogResult.Yes)
{
if (resolveAssemblyFileDialog.ShowDialog(this) == System.Windows.Forms.DialogResult.OK)
{
MyAssembly = Assembly.LoadFrom(resolveAssemblyFileDialog.FileName);
}
else
{
Application.Exit();
}
}
else
Application.Exit();
}
}));
}
return MyAssembly;
}
private void PrintAllPublicMembers(Assembly assembly)
{
foreach (Type type in assembly.GetTypes())
{
stringBuilder.Append("Class/Interface: " + type.Name + Environment.NewLine);
stringBuilder.Append("\tProperties: " + Environment.NewLine);
if (PropertiesCheckBox.Checked)
{
IList<propertyinfo> properties = type.GetProperties(bindingAttributes);
PrintAllProperties(properties);
}
stringBuilder.Append("\tMethods: " + Environment.NewLine);
if (MethodsCheckBox.Checked)
{
IList<methodinfo> methods = type.GetMethods(bindingAttributes);
PrintAllMethods(methods);
}
}
}
private void PrintAllMethods(IList<methodinfo> methods)
{
foreach (var method in methods)
{
stringBuilder.Append("\t\t" + method.Name + Environment.NewLine);
}
}
private void PrintAllProperties(IList<propertyinfo> properties)
{
foreach (PropertyInfo property in properties)
{
IList<object> customAttributes = property.GetCustomAttributes(false);
foreach (var item in customAttributes)
{
}
stringBuilder.Append("\t\t" + property.Name + Environment.NewLine);
}
}
private void TypeAttributesCheckBox_CheckedChanged(object sender, EventArgs e)
{
CheckBox attributeCheckBox = sender as CheckBox;
if (attributeCheckBox != null)
{
attributeCheckBox.Font = new Font(attributeCheckBox.Font, attributeCheckBox.Checked ? FontStyle.Bold : FontStyle.Regular);
}
}
private void FindButton_Click(object sender, EventArgs e)
{
}
}
}
internal static class ExtensionMethods
{
public static string GetCommaSeperatedValue(this IList<string> stringArray)
{
string output = string.Empty;
if (stringArray.Count == 0)
return output;
else if (stringArray.Count == 1)
return (output = stringArray[0]);
else
{
for (int i = 0; i < stringArray.Count; i++)
{
output += "\"" + stringArray[i] + "\"";
if (i < (stringArray.Count - 1))
{
output += " ";
}
}
return output;
}
}
}
</string>