Code:
/ DotNET / DotNET / 8.0 / untmp / WIN_WINDOWS / lh_tools_devdiv_wpf / Windows / wcp / Framework / MS / Internal / AppModel / ResourceContainer.cs / 2 / ResourceContainer.cs
//------------------------------------------------------------------------------
//
//
// Copyright (C) Microsoft Corporation. All rights reserved.
//
//
// Description:
// ResourceContainer is an implementation of the abstract Package class.
// It contains nontrivial overrides for GetPartCore and Exists.
// Many of the methods on Package are not applicable to loading application
// resources, so the ResourceContainer implementations of these methods throw
// the NotSupportedException.
//
// History:
// 10/04/2004: [....]: Initial creation.
// 03/15/2005: [....]: Remove DisposeCore() override since there are no resources
// to release.
// 06/16/2005: [....], Remove DefaultResourceManager, and change the role of
// ResourceManagerWrapper.
//-----------------------------------------------------------------------------
using System;
using System.IO.Packaging;
using System.IO;
using System.Collections.Generic;
using System.Windows.Resources;
using System.Resources;
using System.Reflection;
using System.Globalization;
using MS.Internal.PresentationFramework; // SafeSecurityHelper
using System.Windows;
using System.Windows.Navigation;
using MS.Internal.Resources;
using System.Windows.Interop;
using System.Security;
namespace MS.Internal.AppModel
{
//
// ResourceContainer is an implementation of the abstract Package class.
// It contains nontrivial overrides for GetPartCore and Exists.
// Many of the methods on Package are not applicable to loading application
// resources, so the ResourceContainer implementations of these methods throw
// the NotSupportedException.
//
internal class ResourceContainer : System.IO.Packaging.Package
{
//-----------------------------------------------------
//
// Static Methods
//
//-----------------------------------------------------
#region Static Methods
internal static ResourceManagerWrapper ApplicationResourceManagerWrapper
{
get
{
if (_applicationResourceManagerWrapper == null)
{
// load main excutable assembly
Assembly asmApplication = Application.ResourceAssembly;
if (asmApplication != null)
{
_applicationResourceManagerWrapper = new ResourceManagerWrapper(asmApplication);
}
}
return _applicationResourceManagerWrapper;
}
}
//
// The FileShare mode to use for opening loose files. Currently this defaults to FileShare.Read
// Today it is not changed. If we decide that this should change in the future we can easily add
// a seter here.
//
internal static FileShare FileShare
{
get
{
return _fileShare;
}
}
#endregion
//------------------------------------------------------
//
// Public Constructors
//
//-----------------------------------------------------
#region Public Constructors
//
// Default Constructor
//
internal ResourceContainer() : base(FileAccess.Read)
{
}
#endregion
//------------------------------------------------------
//
// Public Properties
//
//------------------------------------------------------
// None
//-----------------------------------------------------
//
// Public Methods
//
//------------------------------------------------------
#region Public Methods
//
// This method always returns true. This is because ResourceManager does not have a
// simple way to check if a resource exists without loading the resource stream (or failing to)
// so checking if a resource exists would be a very expensive task.
// A part will later be constructed and returned by GetPart(). This part class contains
// a ResourceManager which may or may not contain the requested resource. When someone
// calls GetStream() on PackagePart then we will attempt to get the stream for the named resource
// and potentially fail.
//
//
//
public override bool PartExists(Uri uri)
{
return true;
}
#endregion
//-----------------------------------------------------
//
// Public Events
//
//-----------------------------------------------------
// None
//-----------------------------------------------------
//
// Internal Constructors
//
//------------------------------------------------------
// None
//-----------------------------------------------------
//
// Internal Properties
//
//------------------------------------------------------
#region Internal Members
internal const string XamlExt = ".xaml";
internal const string BamlExt = ".baml";
#endregion
//------------------------------------------------------
//
// Internal Methods
//
//-----------------------------------------------------
// None
//------------------------------------------------------
//
// Internal Events
//
//-----------------------------------------------------
// None
//-----------------------------------------------------
//
// Protected Constructors
//
//-----------------------------------------------------
// None
//------------------------------------------------------
//
// Protected Methods
//
//-----------------------------------------------------
#region Protected Methods
//
// This method creates a part containing the name of the resource and
// the resource manager that should contain it. If the resource manager
// does not contain the requested part then when GetStream() is called on
// the part it will return null.
//
//
//
///
/// 1. Critical - because calling add_AssemblyLoad
/// Safe - because only hooks up specific internal event handler only applicable to for non-browser hosted scneario
/// 2. Critical - because creating a new ResourcePart is critical, as the ResourceManagerWrapper
/// that it uses has an Assembly instance that is SecurityCritical data for accessing internal types.
/// Safe - because a ResourceManagerWrapper is being created based on a Uri name that gets mapped
/// to an assembly from which a stream for the Uri was created and GetResourceManagerWrapper
/// guarantees that given a Uri, the stream is always created from that mapped Assembly
///
[SecurityCritical, SecurityTreatAsSafe]
protected override PackagePart GetPartCore(Uri uri)
{
string partName;
bool isContentFile;
// AppDomain.AssemblyLoad event handler for standalone apps. This is added specifically for designer (Sparkle) scenario.
// We use the assembly name to fetch the cached resource manager. With this mechanism we will still get resource from the
// old version dll when a newer one is loaded. So whenever the AssemblyLoad event is fired, we will need to update the cache
// with the newly loaded assembly. This is currently only for designer so not needed for browser hosted apps.
// Attach the event handler before the first time we get the ResourceManagerWrapper.
if ((! assemblyLoadhandlerAttached) && (! BrowserInteropHelper.IsBrowserHosted))
{
AppDomain.CurrentDomain.AssemblyLoad += new AssemblyLoadEventHandler(OnAssemblyLoadEventHandler);
assemblyLoadhandlerAttached = true;
}
ResourceManagerWrapper rmWrapper = GetResourceManagerWrapper(uri, out partName, out isContentFile);
// If the part name was specified as Content at compile time then we will try to load
// the file directly. Otherwise we assume the user is looking for a resource.
if (isContentFile)
{
return new ContentFilePart(this, uri);
}
else
{
// Uri mapps to a resource stream.
// Make sure the resource id is exactly same as the one we used to create Resource
// at compile time.
partName = ResourceIDHelper.GetResourceIDFromRelativePath(partName);
return new ResourcePart(this, uri, partName, rmWrapper);
}
}
#endregion
//------------------------------------------------------
//
// Private Methods
//
//------------------------------------------------------
#region Private Methods
// AppDomain.AssemblyLoad event handler. Check whether the assembly's resourcemanager has
// been added to the cache. If it has, we need to update the cache with the newly loaded dll.
private void OnAssemblyLoadEventHandler(object sender, AssemblyLoadEventArgs args)
{
Assembly assembly = args.LoadedAssembly;
// This is specific for designer (Sparkle) scenario: rebuild and reload dll using Load(Byte[]).
// We do not care about assemblies loaded into the reflection-only context or the Gaced assemblies.
// For example, in Sparkle whenever a project is built all dependent assemblies will be loaded reflection only.
// We do no care about those. Only when a assembly is loaded into the execution context, we will need to update the cache.
if ((! assembly.ReflectionOnly) && (! assembly.GlobalAssemblyCache))
{
AssemblyName assemblyInfo = new AssemblyName(assembly.FullName);
string assemblyName = assemblyInfo.Name.ToLowerInvariant();
string assemblyKey = string.Empty;
string key = assemblyName;
// Check if this newly loaded assembly is in the cache. If so, update the cache.
// If it is not in cache, do not do anything. It will be added on demand.
// The key could be Name, Name + Version, Name + PublicKeyToken, or Name + Version + PublicKeyToken.
// Otherwise, update the cache with the newly loaded dll.
// First check Name.
UpdateCachedRMW(key, args.LoadedAssembly);
string assemblyVersion = assemblyInfo.Version.ToString();
if (!String.IsNullOrEmpty(assemblyVersion))
{
key = key + assemblyVersion;
// Check Name + Version
UpdateCachedRMW(key, args.LoadedAssembly);
}
byte[] reqKeyToken = assemblyInfo.GetPublicKeyToken();
for (int i = 0; i < reqKeyToken.Length; i++)
{
assemblyKey += reqKeyToken[i].ToString("x", NumberFormatInfo.InvariantInfo);
}
if (!String.IsNullOrEmpty(assemblyKey))
{
key = key + assemblyKey;
// Check Name + Version + KeyToken
UpdateCachedRMW(key, args.LoadedAssembly);
key = assemblyName + assemblyKey;
// Check Name + KeyToken
UpdateCachedRMW(key, args.LoadedAssembly);
}
}
}
private void UpdateCachedRMW(string key, Assembly assembly)
{
if (_registeredResourceManagers.ContainsKey(key))
{
// Update the ResourceManagerWrapper with the new assembly.
// Note Package caches Part and Part holds on to ResourceManagerWrapper. Package does not provide a way for
// us to update their cache, so we update the assembly that the ResourceManagerWrapper holds on to. This way the
// Part cached in the Package class can reference the new dll too.
_registeredResourceManagers[key].Assembly = assembly;
}
}
//
// Searches the available ResourceManagerWrapper list for one that matches the given Uri.
// It could be either ResourceManagerWrapper for specific libary assembly or Application
// main assembly. Package enforces that all Uri will be correctly formated.
//
// Assumed to be relative
// The name of the file in the resource manager
// A flag to indicate that this path is a known loose file at compile time
//
private ResourceManagerWrapper GetResourceManagerWrapper(Uri uri, out string partName, out bool isContentFile)
{
string assemblyName;
string assemblyVersion;
string assemblyKey;
ResourceManagerWrapper rmwResult = ApplicationResourceManagerWrapper;
isContentFile = false;
BaseUriHelper.GetAssemblyNameAndPart(uri, out partName, out assemblyName, out assemblyVersion, out assemblyKey);
if (!String.IsNullOrEmpty(assemblyName))
{
string key = assemblyName + assemblyVersion + assemblyKey;
_registeredResourceManagers.TryGetValue(key.ToLowerInvariant(), out rmwResult);
// first time. Add this to the hash table
if (rmwResult == null)
{
Assembly assembly;
assembly = BaseUriHelper.GetLoadedAssembly(assemblyName, assemblyVersion, assemblyKey);
if (assembly.Equals(Application.ResourceAssembly))
{
// This Uri maps to Application Entry assembly even though it has ";component".
rmwResult = ApplicationResourceManagerWrapper;
}
else
{
rmwResult = new ResourceManagerWrapper(assembly);
}
_registeredResourceManagers[key.ToLowerInvariant()] = rmwResult;
}
}
if ((rmwResult == ApplicationResourceManagerWrapper) && (rmwResult != null))
{
// If this is not a resource from a component then it might be
// a content file and not an application resource.
if (ContentFileHelper.IsContentFile(partName))
{
isContentFile = true;
rmwResult = null;
}
}
return rmwResult;
}
#endregion
//-----------------------------------------------------
//
// Private Fields
//
//------------------------------------------------------
#region Private Members
private static Dictionary _registeredResourceManagers = new Dictionary();
private static ResourceManagerWrapper _applicationResourceManagerWrapper = null;
private static FileShare _fileShare = FileShare.Read;
private static bool assemblyLoadhandlerAttached = false;
#endregion Private Members
//-----------------------------------------------------
//
// Uninteresting (but required) overrides
//
//-----------------------------------------------------
#region Uninteresting (but required) overrides
protected override PackagePart CreatePartCore(Uri uri, string contentType, CompressionOption compressionOption)
{
return null;
}
protected override void DeletePartCore(Uri uri)
{
throw new NotSupportedException();
}
protected override PackagePart[] GetPartsCore()
{
throw new NotSupportedException();
}
protected override void FlushCore()
{
throw new NotSupportedException();
}
#endregion
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- ColumnBinding.cs
- PluralizationServiceUtil.cs
- WCFBuildProvider.cs
- MSAAWinEventWrap.cs
- Asn1IntegerConverter.cs
- DataError.cs
- BooleanToVisibilityConverter.cs
- ToolBarOverflowPanel.cs
- SelectionEditor.cs
- RuntimeResourceSet.cs
- ConnectionInterfaceCollection.cs
- LicenseManager.cs
- WebEvents.cs
- TreeViewCancelEvent.cs
- DbgUtil.cs
- Wildcard.cs
- StaticDataManager.cs
- AutomationPatternInfo.cs
- SqlNode.cs
- WebBrowserBase.cs
- ListViewItemSelectionChangedEvent.cs
- AnonymousIdentificationModule.cs
- WriteFileContext.cs
- SchemaDeclBase.cs
- Track.cs
- UnitySerializationHolder.cs
- ConfigurationElementCollection.cs
- OperationCanceledException.cs
- VerificationException.cs
- ILGen.cs
- ToolboxItemImageConverter.cs
- ObjectSelectorEditor.cs
- SingleTagSectionHandler.cs
- NativeMethods.cs
- InputBinding.cs
- EntityViewGenerationConstants.cs
- TableLayoutRowStyleCollection.cs
- TripleDESCryptoServiceProvider.cs
- CustomAttributeSerializer.cs
- PointKeyFrameCollection.cs
- TypographyProperties.cs
- WebPartZoneBase.cs
- StateManagedCollection.cs
- MediaContextNotificationWindow.cs
- Transform.cs
- RequestBringIntoViewEventArgs.cs
- DrawingContextWalker.cs
- EtwProvider.cs
- FocusManager.cs
- CompilerTypeWithParams.cs
- AddInPipelineAttributes.cs
- ListBoxItemWrapperAutomationPeer.cs
- ClientScriptManagerWrapper.cs
- SubtreeProcessor.cs
- QueryReaderSettings.cs
- pingexception.cs
- WmiPutTraceRecord.cs
- TypeSystem.cs
- AddressAlreadyInUseException.cs
- SqlGatherProducedAliases.cs
- ExpressionPrefixAttribute.cs
- SchemaImporterExtension.cs
- HelpInfo.cs
- DebugHandleTracker.cs
- Cursor.cs
- TargetConverter.cs
- PublishLicense.cs
- Membership.cs
- OleDbTransaction.cs
- SafeHandle.cs
- SchemaManager.cs
- Baml2006KeyRecord.cs
- HttpListenerException.cs
- WebPartConnectionsCancelVerb.cs
- CustomAttributeFormatException.cs
- MouseEvent.cs
- XmlDataSourceNodeDescriptor.cs
- DataObjectSettingDataEventArgs.cs
- PointHitTestParameters.cs
- DocumentViewerConstants.cs
- DeclaredTypeValidator.cs
- XamlNamespaceHelper.cs
- X509CertificateValidator.cs
- CompleteWizardStep.cs
- TagPrefixInfo.cs
- HttpGetClientProtocol.cs
- DataSetMappper.cs
- ThreadStateException.cs
- CriticalFileToken.cs
- KeyboardNavigation.cs
- InternalConfigConfigurationFactory.cs
- BooleanExpr.cs
- WindowInteractionStateTracker.cs
- ScrollItemProviderWrapper.cs
- SecuritySessionSecurityTokenAuthenticator.cs
- DispatchChannelSink.cs
- ProfileProvider.cs
- ProviderCollection.cs
- EventDescriptor.cs
- XmlCharCheckingWriter.cs