Code:
/ 4.0 / 4.0 / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / clr / src / BCL / System / Runtime / Serialization / SurrogateSelector.cs / 1305376 / SurrogateSelector.cs
using System.Diagnostics.Contracts;
// ==++==
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
// ==--==
/*============================================================
**
** Class: SurrogateSelector
**
**
** Purpose: A user-supplied class for doing the type to surrogate
** mapping.
**
**
===========================================================*/
namespace System.Runtime.Serialization {
using System.Runtime.Remoting;
using System;
using System.Collections;
using System.Security.Permissions;
[System.Runtime.InteropServices.ComVisible(true)]
public class SurrogateSelector : ISurrogateSelector {
internal SurrogateHashtable m_surrogates;
internal ISurrogateSelector m_nextSelector;
public SurrogateSelector() {
m_surrogates = new SurrogateHashtable(32);
}
// Adds a surrogate to the list of surrogates checked.
public virtual void AddSurrogate(Type type, StreamingContext context, ISerializationSurrogate surrogate) {
if (type==null) {
throw new ArgumentNullException("type");
}
if (surrogate==null) {
throw new ArgumentNullException("surrogate");
}
Contract.EndContractBlock();
SurrogateKey key = new SurrogateKey(type, context);
m_surrogates.Add(key, surrogate); // Hashtable does duplicate checking.
}
[System.Security.SecurityCritical] // auto-generated
private static bool HasCycle(ISurrogateSelector selector) {
ISurrogateSelector head;
ISurrogateSelector tail;
Contract.Assert(selector!=null, "[HasCycle]selector!=null");
head = selector;
tail = selector;
while (head!=null) {
head = head.GetNextSelector();
if (head==null) {
return true;
}
if (head==tail) {
return false;
}
head = head.GetNextSelector();
tail = tail.GetNextSelector();
if (head==tail) {
return false;
}
}
return true;
}
// Adds another selector to check if we don't have match within this selector.
// The logic is:"Add this onto the list as the first thing that you check after yourself."
[System.Security.SecurityCritical] // auto-generated_required
public virtual void ChainSelector(ISurrogateSelector selector) {
ISurrogateSelector temp;
ISurrogateSelector tempCurr;
ISurrogateSelector tempPrev;
ISurrogateSelector tempEnd;
if (selector==null) {
throw new ArgumentNullException("selector");
}
Contract.EndContractBlock();
//
// Verify that we don't try and add ourself twice.
//
if (selector==this) {
throw new SerializationException(Environment.GetResourceString("Serialization_DuplicateSelector"));
}
//
// Verify that the argument doesn't contain a cycle.
//
if (!HasCycle(selector)) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycleInArgument"), "selector");
}
//
// Check for a cycle that would lead back to this. We find the end of the list that we're being asked to
// insert for use later.
//
tempCurr = selector.GetNextSelector();
tempEnd = selector;
while (tempCurr!=null && tempCurr!=this) {
tempEnd = tempCurr;
tempCurr = tempCurr.GetNextSelector();
}
if (tempCurr==this) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycle"), "selector");
}
//
// Check for a cycle later in the list which would be introduced by this insertion.
//
tempCurr = selector;
tempPrev = selector;
while(tempCurr!=null) {
if (tempCurr==tempEnd) {
tempCurr = this.GetNextSelector();
} else {
tempCurr = tempCurr.GetNextSelector();
}
if (tempCurr==null) {
break;
}
if (tempCurr==tempPrev) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycle"), "selector");
}
if (tempCurr==tempEnd) {
tempCurr = this.GetNextSelector();
} else {
tempCurr = tempCurr.GetNextSelector();
}
if (tempPrev==tempEnd) {
tempPrev = this.GetNextSelector();
} else {
tempPrev = tempPrev.GetNextSelector();
}
if (tempCurr==tempPrev) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycle"), "selector");
}
}
//
// Add the new selector and it's entire chain of selectors as the next thing that
// we check.
//
temp = m_nextSelector;
m_nextSelector = selector;
if (temp!=null) {
tempEnd.ChainSelector(temp);
}
}
// Get the next selector on the chain of selectors.
[System.Security.SecurityCritical] // auto-generated_required
public virtual ISurrogateSelector GetNextSelector() {
return m_nextSelector;
}
// Gets the surrogate for a particular type. If this selector can't
// provide a surrogate, it checks with all of it's children before returning null.
[System.Security.SecurityCritical] // auto-generated_required
public virtual ISerializationSurrogate GetSurrogate(Type type, StreamingContext context, out ISurrogateSelector selector) {
if (type==null) {
throw new ArgumentNullException("type");
}
Contract.EndContractBlock();
selector = this;
SurrogateKey key = new SurrogateKey(type, context);
ISerializationSurrogate temp = (ISerializationSurrogate)m_surrogates[key];
if (temp!=null) {
return temp;
}
if (m_nextSelector!=null) {
return m_nextSelector.GetSurrogate(type, context, out selector);
}
return null;
}
// Removes the surrogate associated with a given type. Does not
// check chained surrogates.
public virtual void RemoveSurrogate(Type type, StreamingContext context) {
if (type==null) {
throw new ArgumentNullException("type");
}
Contract.EndContractBlock();
SurrogateKey key = new SurrogateKey(type, context);
m_surrogates.Remove(key);
}
}
//<
[Serializable]
internal class SurrogateKey {
internal Type m_type;
internal StreamingContext m_context;
internal SurrogateKey(Type type, StreamingContext context) {
m_type = type;
m_context = context;
}
public override int GetHashCode() {
return m_type.GetHashCode();
}
}
// Subclass to override KeyEquals.
class SurrogateHashtable : Hashtable {
internal SurrogateHashtable(int size):base(size){
;
}
// Must return true if the context to serialize for (givenContext)
// is a subset of the context for which the serialization selector is provided (presentContext)
// Note: This is done by overriding KeyEquals rather than overriding Equals() in the SurrogateKey
// class because Equals() method must be commutative.
protected override bool KeyEquals(Object key, Object item){
SurrogateKey givenValue = (SurrogateKey)item;
SurrogateKey presentValue = (SurrogateKey)key;
return presentValue.m_type == givenValue.m_type &&
(presentValue.m_context.m_state & givenValue.m_context.m_state) == givenValue.m_context.m_state &&
presentValue.m_context.Context == givenValue.m_context.Context;
}
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
using System.Diagnostics.Contracts;
// ==++==
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
// ==--==
/*============================================================
**
** Class: SurrogateSelector
**
**
** Purpose: A user-supplied class for doing the type to surrogate
** mapping.
**
**
===========================================================*/
namespace System.Runtime.Serialization {
using System.Runtime.Remoting;
using System;
using System.Collections;
using System.Security.Permissions;
[System.Runtime.InteropServices.ComVisible(true)]
public class SurrogateSelector : ISurrogateSelector {
internal SurrogateHashtable m_surrogates;
internal ISurrogateSelector m_nextSelector;
public SurrogateSelector() {
m_surrogates = new SurrogateHashtable(32);
}
// Adds a surrogate to the list of surrogates checked.
public virtual void AddSurrogate(Type type, StreamingContext context, ISerializationSurrogate surrogate) {
if (type==null) {
throw new ArgumentNullException("type");
}
if (surrogate==null) {
throw new ArgumentNullException("surrogate");
}
Contract.EndContractBlock();
SurrogateKey key = new SurrogateKey(type, context);
m_surrogates.Add(key, surrogate); // Hashtable does duplicate checking.
}
[System.Security.SecurityCritical] // auto-generated
private static bool HasCycle(ISurrogateSelector selector) {
ISurrogateSelector head;
ISurrogateSelector tail;
Contract.Assert(selector!=null, "[HasCycle]selector!=null");
head = selector;
tail = selector;
while (head!=null) {
head = head.GetNextSelector();
if (head==null) {
return true;
}
if (head==tail) {
return false;
}
head = head.GetNextSelector();
tail = tail.GetNextSelector();
if (head==tail) {
return false;
}
}
return true;
}
// Adds another selector to check if we don't have match within this selector.
// The logic is:"Add this onto the list as the first thing that you check after yourself."
[System.Security.SecurityCritical] // auto-generated_required
public virtual void ChainSelector(ISurrogateSelector selector) {
ISurrogateSelector temp;
ISurrogateSelector tempCurr;
ISurrogateSelector tempPrev;
ISurrogateSelector tempEnd;
if (selector==null) {
throw new ArgumentNullException("selector");
}
Contract.EndContractBlock();
//
// Verify that we don't try and add ourself twice.
//
if (selector==this) {
throw new SerializationException(Environment.GetResourceString("Serialization_DuplicateSelector"));
}
//
// Verify that the argument doesn't contain a cycle.
//
if (!HasCycle(selector)) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycleInArgument"), "selector");
}
//
// Check for a cycle that would lead back to this. We find the end of the list that we're being asked to
// insert for use later.
//
tempCurr = selector.GetNextSelector();
tempEnd = selector;
while (tempCurr!=null && tempCurr!=this) {
tempEnd = tempCurr;
tempCurr = tempCurr.GetNextSelector();
}
if (tempCurr==this) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycle"), "selector");
}
//
// Check for a cycle later in the list which would be introduced by this insertion.
//
tempCurr = selector;
tempPrev = selector;
while(tempCurr!=null) {
if (tempCurr==tempEnd) {
tempCurr = this.GetNextSelector();
} else {
tempCurr = tempCurr.GetNextSelector();
}
if (tempCurr==null) {
break;
}
if (tempCurr==tempPrev) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycle"), "selector");
}
if (tempCurr==tempEnd) {
tempCurr = this.GetNextSelector();
} else {
tempCurr = tempCurr.GetNextSelector();
}
if (tempPrev==tempEnd) {
tempPrev = this.GetNextSelector();
} else {
tempPrev = tempPrev.GetNextSelector();
}
if (tempCurr==tempPrev) {
throw new ArgumentException(Environment.GetResourceString("Serialization_SurrogateCycle"), "selector");
}
}
//
// Add the new selector and it's entire chain of selectors as the next thing that
// we check.
//
temp = m_nextSelector;
m_nextSelector = selector;
if (temp!=null) {
tempEnd.ChainSelector(temp);
}
}
// Get the next selector on the chain of selectors.
[System.Security.SecurityCritical] // auto-generated_required
public virtual ISurrogateSelector GetNextSelector() {
return m_nextSelector;
}
// Gets the surrogate for a particular type. If this selector can't
// provide a surrogate, it checks with all of it's children before returning null.
[System.Security.SecurityCritical] // auto-generated_required
public virtual ISerializationSurrogate GetSurrogate(Type type, StreamingContext context, out ISurrogateSelector selector) {
if (type==null) {
throw new ArgumentNullException("type");
}
Contract.EndContractBlock();
selector = this;
SurrogateKey key = new SurrogateKey(type, context);
ISerializationSurrogate temp = (ISerializationSurrogate)m_surrogates[key];
if (temp!=null) {
return temp;
}
if (m_nextSelector!=null) {
return m_nextSelector.GetSurrogate(type, context, out selector);
}
return null;
}
// Removes the surrogate associated with a given type. Does not
// check chained surrogates.
public virtual void RemoveSurrogate(Type type, StreamingContext context) {
if (type==null) {
throw new ArgumentNullException("type");
}
Contract.EndContractBlock();
SurrogateKey key = new SurrogateKey(type, context);
m_surrogates.Remove(key);
}
}
//<
[Serializable]
internal class SurrogateKey {
internal Type m_type;
internal StreamingContext m_context;
internal SurrogateKey(Type type, StreamingContext context) {
m_type = type;
m_context = context;
}
public override int GetHashCode() {
return m_type.GetHashCode();
}
}
// Subclass to override KeyEquals.
class SurrogateHashtable : Hashtable {
internal SurrogateHashtable(int size):base(size){
;
}
// Must return true if the context to serialize for (givenContext)
// is a subset of the context for which the serialization selector is provided (presentContext)
// Note: This is done by overriding KeyEquals rather than overriding Equals() in the SurrogateKey
// class because Equals() method must be commutative.
protected override bool KeyEquals(Object key, Object item){
SurrogateKey givenValue = (SurrogateKey)item;
SurrogateKey presentValue = (SurrogateKey)key;
return presentValue.m_type == givenValue.m_type &&
(presentValue.m_context.m_state & givenValue.m_context.m_state) == givenValue.m_context.m_state &&
presentValue.m_context.Context == givenValue.m_context.Context;
}
}
}
// 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
- WaitHandleCannotBeOpenedException.cs
- TreeWalker.cs
- SelectionWordBreaker.cs
- OLEDB_Util.cs
- ControlBindingsCollection.cs
- ProtocolElement.cs
- WebPartConnectionsConfigureVerb.cs
- ProcessHost.cs
- XmlRootAttribute.cs
- HorizontalAlignConverter.cs
- QueryValue.cs
- SqlDataSourceDesigner.cs
- ToolZone.cs
- MappingModelBuildProvider.cs
- RuntimeHelpers.cs
- XomlCompilerHelpers.cs
- NavigationProperty.cs
- ZipFileInfo.cs
- StrokeNodeData.cs
- DesignerAttribute.cs
- configsystem.cs
- ServiceSecurityContext.cs
- PersonalizationStateInfoCollection.cs
- EpmTargetPathSegment.cs
- TemplateBindingExpression.cs
- SystemException.cs
- ExtendedPropertyDescriptor.cs
- DelayedRegex.cs
- SchemaCompiler.cs
- ColorConvertedBitmap.cs
- HScrollBar.cs
- XmlCollation.cs
- MbpInfo.cs
- AxHost.cs
- GCHandleCookieTable.cs
- TextContainerChangedEventArgs.cs
- DbDataReader.cs
- ContentElement.cs
- CompilerLocalReference.cs
- EntityContainerEmitter.cs
- SocketInformation.cs
- ZipPackage.cs
- RotateTransform3D.cs
- XmlNamespaceManager.cs
- EpmContentDeSerializerBase.cs
- XPathDescendantIterator.cs
- listitem.cs
- IPipelineRuntime.cs
- AutoGeneratedFieldProperties.cs
- XmlArrayItemAttributes.cs
- FrameworkPropertyMetadata.cs
- SingleStorage.cs
- TrackingProfile.cs
- EventLogQuery.cs
- GCHandleCookieTable.cs
- RootBrowserWindowProxy.cs
- AppDomainUnloadedException.cs
- EntityDataSourceValidationException.cs
- SecurityDescriptor.cs
- HttpContext.cs
- JsonQNameDataContract.cs
- LayeredChannelListener.cs
- ListenerSessionConnectionReader.cs
- Brush.cs
- TraceSource.cs
- KeyValueInternalCollection.cs
- SettingsPropertyIsReadOnlyException.cs
- FormsAuthenticationEventArgs.cs
- WebPartEditVerb.cs
- ModuleBuilder.cs
- BordersPage.cs
- XmlSchemaValidationException.cs
- Unit.cs
- DataGrid.cs
- FontInfo.cs
- XslVisitor.cs
- PropertyRecord.cs
- ComUdtElement.cs
- AttachedAnnotationChangedEventArgs.cs
- MetaForeignKeyColumn.cs
- XsltInput.cs
- HtmlLink.cs
- ColorTransformHelper.cs
- VariableQuery.cs
- EmptyCollection.cs
- UpdateInfo.cs
- FactoryGenerator.cs
- SmiEventSink.cs
- RSAPKCS1KeyExchangeDeformatter.cs
- ViewgenContext.cs
- DataBoundLiteralControl.cs
- WebPartTransformerCollection.cs
- CheckBox.cs
- SqlDataSourceCache.cs
- FreezableCollection.cs
- TakeQueryOptionExpression.cs
- ITextView.cs
- CodeTypeDeclarationCollection.cs
- NameObjectCollectionBase.cs
- Zone.cs