Code:
/ 4.0 / 4.0 / untmp / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / fx / src / DataEntity / System / Data / Metadata / ObjectLayer / AssemblyCache.cs / 1305376 / AssemblyCache.cs
//----------------------------------------------------------------------
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
//
// @owner [....]
// @backupOwner [....]
//---------------------------------------------------------------------
using System.Collections.Generic;
using System.Data.Common.Utils;
using System.Diagnostics;
using System.Reflection;
namespace System.Data.Metadata.Edm
{
internal static class AssemblyCache
{
// Global Assembly Cache
private readonly static Dictionary s_globalAssemblyCache = new Dictionary();
private static object _assemblyCacheLock = new object();
//List of assemblies having view gen attribute. We cache these things if we discover
//these assemblies while looking for O-space metadata.
private static IList s_viewGenAssemblies = new ThreadSafeList();
internal static LockedAssemblyCache AquireLockedAssemblyCache()
{
return new LockedAssemblyCache(_assemblyCacheLock, s_globalAssemblyCache);
}
internal static void LoadAssembly(Assembly assembly, bool loadReferencedAssemblies,
KnownAssembliesSet knownAssemblies, out Dictionary typesInLoading, out List errors)
{
object loaderCookie = null;
LoadAssembly(assembly, loadReferencedAssemblies, knownAssemblies, null, null, ref loaderCookie, out typesInLoading, out errors);
}
internal static void LoadAssembly(Assembly assembly, bool loadReferencedAssemblies,
KnownAssembliesSet knownAssemblies, EdmItemCollection edmItemCollection, Action logLoadMessage, ref object loaderCookie, out Dictionary typesInLoading, out List errors)
{
Debug.Assert(loaderCookie == null || loaderCookie is Func, "This is a bad loader cookie");
typesInLoading = null;
errors = null;
using (LockedAssemblyCache lockedAssemblyCache = AssemblyCache.AquireLockedAssemblyCache())
{
ObjectItemLoadingSessionData loadingData = new ObjectItemLoadingSessionData(knownAssemblies, lockedAssemblyCache, edmItemCollection, logLoadMessage, loaderCookie);
LoadAssembly(assembly, loadReferencedAssemblies, loadingData);
loaderCookie = loadingData.LoaderCookie;
// resolve references to top level types (base types, navigation properties returns and associations, and complex type properties)
loadingData.CompleteSession();
if (loadingData.EdmItemErrors.Count == 0)
{
// do the validation for the all the new types
// Now, perform validation on all the new types
EdmValidator validator = new EdmValidator();
validator.SkipReadOnlyItems = true;
validator.Validate(loadingData.TypesInLoading.Values, loadingData.EdmItemErrors);
// Update the global cache if there are no errors
if (loadingData.EdmItemErrors.Count == 0)
{
if (ObjectItemAssemblyLoader.IsAttributeLoader(loadingData.ObjectItemAssemblyLoaderFactory))
{
// we only cache items from the attribute loader globally, the
// items loaded by convention will change depending on the cspace
// provided. cspace will have a cache of it's own for assemblies
UpdateCache(lockedAssemblyCache, loadingData.AssembliesLoaded);
}
else if (loadingData.EdmItemCollection != null &&
ObjectItemAssemblyLoader.IsConventionLoader(loadingData.ObjectItemAssemblyLoaderFactory))
{
UpdateCache(loadingData.EdmItemCollection, loadingData.AssembliesLoaded);
}
}
}
if (loadingData.TypesInLoading.Count > 0)
{
foreach (EdmType edmType in loadingData.TypesInLoading.Values)
{
edmType.SetReadOnly();
}
}
// Update the out parameters once you are done with loading
typesInLoading = loadingData.TypesInLoading;
errors = loadingData.EdmItemErrors;
}
}
private static void LoadAssembly(Assembly assembly, bool loadReferencedAssemblies, ObjectItemLoadingSessionData loadingData)
{
// Check if the assembly is already loaded
KnownAssemblyEntry entry;
bool shouldLoadReferences = false;
if (loadingData.KnownAssemblies.TryGetKnownAssembly(assembly, loadingData.ObjectItemAssemblyLoaderFactory, loadingData.EdmItemCollection, out entry))
{
shouldLoadReferences = !entry.ReferencedAssembliesAreLoaded && loadReferencedAssemblies;
}
else
{
ObjectItemAssemblyLoader loader = ObjectItemAssemblyLoader.CreateLoader(assembly, loadingData);
loader.Load();
shouldLoadReferences = loadReferencedAssemblies;
}
if (shouldLoadReferences)
{
if (entry == null && loadingData.KnownAssemblies.TryGetKnownAssembly(assembly, loadingData.ObjectItemAssemblyLoaderFactory, loadingData.EdmItemCollection, out entry) ||
entry != null)
{
entry.ReferencedAssembliesAreLoaded = true;
}
Debug.Assert(entry != null, "we should always have an entry, why don't we?");
// We will traverse through all the statically linked assemblies and their dependencies.
// Only assemblies with the EdmSchemaAttribute will be loaded and rest will be ignored
// Even if the schema attribute is missing, we should still check all the dependent assemblies
// any of the dependent assemblies can have the schema attribute
// After the given assembly has been loaded, check on the flag in _knownAssemblies to see if it has already
// been recursively loaded. The flag can be true if it was already loaded before this function was called
foreach (Assembly referencedAssembly in MetadataAssemblyHelper.GetNonSystemReferencedAssemblies(assembly))
{
// filter out "known" assemblies to prevent unnecessary loading
EntityBid.Trace(" loadededAssembly='%ls'\n", referencedAssembly.FullName);
// recursive call
LoadAssembly(referencedAssembly, loadReferencedAssemblies, loadingData);
}
}
}
private static void UpdateCache(EdmItemCollection edmItemCollection, Dictionary assemblies)
{
foreach (var entry in assemblies)
{
edmItemCollection.ConventionalOcCache.AddAssemblyToOcCacheFromAssemblyCache(
entry.Key, new ImmutableAssemblyCacheEntry(entry.Value));
}
}
private static void UpdateCache(LockedAssemblyCache lockedAssemblyCache, Dictionary assemblies)
{
foreach (KeyValuePair entry in assemblies)
{
// Add all the assemblies from the loading context to the global cache
lockedAssemblyCache.Add(entry.Key, new ImmutableAssemblyCacheEntry(entry.Value));
}
}
internal static IList ViewGenerationAssemblies
{
get
{
return s_viewGenAssemblies;
}
}
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- TrackingStringDictionary.cs
- Qualifier.cs
- DataControlFieldCell.cs
- HttpInputStream.cs
- SystemNetworkInterface.cs
- PerformanceCounterPermission.cs
- FormCollection.cs
- SqlTypeSystemProvider.cs
- CngAlgorithmGroup.cs
- SizeAnimationBase.cs
- PassportAuthenticationEventArgs.cs
- DescendantBaseQuery.cs
- WebPartConnectionsCancelEventArgs.cs
- IsolatedStorageFileStream.cs
- FactoryGenerator.cs
- HtmlElementEventArgs.cs
- ServicesUtilities.cs
- XPathDocumentIterator.cs
- ServiceDescriptionSerializer.cs
- TransformDescriptor.cs
- XXXInfos.cs
- VScrollBar.cs
- WorkflowMarkupSerializer.cs
- SqlInternalConnectionTds.cs
- RowBinding.cs
- SamlAdvice.cs
- XsltArgumentList.cs
- EntityClientCacheEntry.cs
- ExtendedPropertyDescriptor.cs
- EntityConnection.cs
- Size.cs
- DbConnectionPoolGroupProviderInfo.cs
- CompatibleComparer.cs
- MinMaxParagraphWidth.cs
- DBCSCodePageEncoding.cs
- HashLookup.cs
- Config.cs
- DPCustomTypeDescriptor.cs
- ColorConvertedBitmap.cs
- FlowDocumentPaginator.cs
- SymmetricKeyWrap.cs
- SafeFileMappingHandle.cs
- ConversionValidationRule.cs
- DataSetMappper.cs
- NumericUpDownAccelerationCollection.cs
- SpecialFolderEnumConverter.cs
- WindowsFont.cs
- DbConnectionPoolOptions.cs
- TextEndOfLine.cs
- RectAnimationBase.cs
- DataFormat.cs
- Message.cs
- TimeSpanValidator.cs
- CacheRequest.cs
- CustomSignedXml.cs
- QilName.cs
- ContractUtils.cs
- MenuItemBinding.cs
- DataGridBoolColumn.cs
- TabPageDesigner.cs
- MdImport.cs
- figurelength.cs
- HttpDebugHandler.cs
- TimeSpanConverter.cs
- StructuredTypeEmitter.cs
- DefaultClaimSet.cs
- TriggerActionCollection.cs
- NullEntityWrapper.cs
- DateTimeConstantAttribute.cs
- RuntimeDelegateArgument.cs
- DES.cs
- XmlNodeReader.cs
- InputDevice.cs
- ProfileManager.cs
- Expression.cs
- File.cs
- DesignerContextDescriptor.cs
- XmlDataSourceView.cs
- PrimitiveCodeDomSerializer.cs
- SqlParameter.cs
- TransportContext.cs
- SafeRightsManagementQueryHandle.cs
- ConfigurationUtility.cs
- DecodeHelper.cs
- Selection.cs
- WindowsFormsHostPropertyMap.cs
- PassportAuthenticationEventArgs.cs
- DoubleLinkList.cs
- CharacterBuffer.cs
- SplineKeyFrames.cs
- SecurityTokenRequirement.cs
- XmlQualifiedName.cs
- EventSinkHelperWriter.cs
- ConfigXmlSignificantWhitespace.cs
- ContextMenu.cs
- ZipIOZip64EndOfCentralDirectoryLocatorBlock.cs
- AsymmetricKeyExchangeFormatter.cs
- WebAdminConfigurationHelper.cs
- FontDialog.cs
- SqlCommandSet.cs