} // public Root property #endregion // Public Properties #region Private Methods private void InitializeInstance( ) { AssemblyName [] aasmNames = _asmRoot.GetReferencedAssemblies( ); _lstNamesOfDependentAssemblies = new List <DependentAssemblyInfo> (aasmNames.Length); foreach (AssemblyName asmName in aasmNames) { _lstNamesOfDependentAssemblies.Add( new DependentAssemblyInfo(asmName)); } // foreach ( AssemblyName asmName in aasmNames ) _lstNamesOfDependentAssemblies.Sort( ); // Sorting is a prerequisite of the binary search algorithm. // ---------------------------------------------------------------- // Identify and mark dependents that are currently loaded. // ---------------------------------------------------------------- Assembly [] asmAlreadyLoaded = AppDomain.CurrentDomain.GetAssemblies( ); foreach (Assembly asmDependent in asmAlreadyLoaded) { DependentAssemblyInfo daiCurrent = new DependentAssemblyInfo(asmDependent.GetName( )); int intMatch = _lstNamesOfDependentAssemblies.BinarySearch(daiCurrent); if (intMatch > ListInfo.BINARY_SEARCH_NOT_FOUND) { _lstNamesOfDependentAssemblies [intMatch].MarkAsLoaded(asmDependent); } // if ( intMatch > ListInfo.BINARY_SEARCH_NOT_FOUND ) } // foreach ( Assembly asmDependent in asmAlreadyLoaded ) } // InitializeInstance
} // DestroyDependents /// <summary> /// List the properties of each dependent assembly. /// </summary> /// <param name="pswOut"> /// Specify the optional output StreamWriter onto which the dependent /// assembly details are to be written. The default value is NULL, which /// suppresses output. /// </param> /// <param name="pchrDelimiter"> /// Specify the optional field delimiter. The default value is a comma. /// </param> public void DisplayProperties( StreamWriter pswOut = null, char pchrDelimiter = SpecialCharacters.COMMA) { Console.WriteLine( Properties.Resources.MSG_ASM_DEPENDENTS_DETAILS_HEAD, // Format Control String Environment.NewLine); // Format Item 2 = Embedded Newline // ---------------------------------------------------------------- // Load any dependents that haven't already loaded in due course. // Each of these DLLs loads into a private Application Domain, so // that it can be unloaded before the collection goes out scope. // // Deferring this operation until this routine executes means that // DestroyDependents need not be called unless this method runs. // ---------------------------------------------------------------- if (pswOut != null) { // If present, the stream is expected to be open for writing. ReportGenerators.LabelKeyAssemblyProperties( pswOut, pchrDelimiter); } // if ( pswOut != null ) int intNDependents = _lstNamesOfDependentAssemblies.Count; for (int intJ = ArrayInfo.ARRAY_FIRST_ELEMENT; intJ < intNDependents; intJ++) { // Load dependents that haven't already been loaded. DependentAssemblyInfo daiCurrent = _lstNamesOfDependentAssemblies [intJ]; if (!daiCurrent.IsLoaded) { // Load the assembly into a dedicated AppDomain, so that it can be unloaded. daiCurrent.LoadForInspection( ); } // FALSE (The application created a custom domain, into which it loaded the assembly.) block, if ( daiCurrent.IsLoaded ) ReportGenerators.ShowKeyAssemblyProperties( daiCurrent.AssemblyDetails, intJ, intNDependents); if (pswOut != null) { // If present, the stream is expected to be open for writing. ReportGenerators.ListKeyAssemblyProperties( daiCurrent.AssemblyDetails, pswOut, pchrDelimiter); } // if ( pswOut != null ) } // for ( int intJ = ArrayInfo.ARRAY_FIRST_ELEMENT ; intJ < intNDependents ; intJ++ ) Console.WriteLine( Properties.Resources.MSG_ASM_DEPENDENTS_DETAILS_TAIL, // Format Control String _asmRoot.FullName, // Format Item 0 = Assembly Full Name Environment.NewLine); // Format Item 1 = Embedded Newline DestroyDependents( ); } // DisplayProperties method
} // public Root property #endregion // Public Properties #region Private Methods private void InitializeInstance( ) { AssemblyName [] aasmNames = _asmRoot.GetReferencedAssemblies( ); _lstNamesOfDependentAssemblies = new List <DependentAssemblyInfo> (aasmNames.Length); { // Build a scope fence around loop index intNDependents. int intNDependents = aasmNames.Length; for (int intJ = ArrayInfo.ARRAY_FIRST_ELEMENT; intJ < intNDependents; intJ++) { _lstNamesOfDependentAssemblies.Add(new DependentAssemblyInfo(aasmNames [intJ])); } // for ( int intJ = ArrayInfo.ARRAY_FIRST_ELEMENT ; intJ < intNDependents ; intJ++ ) } // Let intNDependents go out of scope. _lstNamesOfDependentAssemblies.Sort( ); // Sorting is a prerequisite of the binary search algorithm. // ---------------------------------------------------------------- // Identify and mark dependents that are currently loaded. // ---------------------------------------------------------------- Assembly [] asmAlreadyLoaded = AppDomain.CurrentDomain.GetAssemblies( ); { // Build a scope fence around loop index intNLoadedDependents. int intNLoadedDependents = asmAlreadyLoaded.Length; for (int intJ = ArrayInfo.ARRAY_FIRST_ELEMENT; intJ < intNLoadedDependents; intJ++) { DependentAssemblyInfo daiCurrent = new DependentAssemblyInfo(asmAlreadyLoaded [intJ].GetName( )); int intMatch = _lstNamesOfDependentAssemblies.BinarySearch(daiCurrent); if (intMatch > ListInfo.BINARY_SEARCH_NOT_FOUND) { _lstNamesOfDependentAssemblies [intMatch].MarkAsLoaded(asmAlreadyLoaded [intJ]); } // if ( intMatch > ListInfo.BINARY_SEARCH_NOT_FOUND ) } // for ( int intJ = ArrayInfo.ARRAY_FIRST_ELEMENT ; intJ < intNLoadedDependents ; intJ++ ) } // Let intNLoadedDependents go out of scope. (This is insurance against new code being added below that extends the scope of the method.) } // InitializeInstance