Code:
/ 4.0 / 4.0 / untmp / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / clr / src / ManagedLibraries / Remoting / Channels / Sinks / BinaryFormatterSinks.cs / 1305376 / BinaryFormatterSinks.cs
// ==++== // // Copyright (c) Microsoft Corporation. All rights reserved. // // ==--== //========================================================================== // File: BinaryFormatterSinks.cs // // Summary: Binary formatter client and server sinks. // //========================================================================= using System; using System.Collections; using System.IO; using System.Reflection; using System.Runtime.Serialization.Formatters; using System.Runtime.Remoting; using System.Runtime.Remoting.Channels; using System.Runtime.Remoting.Channels.Http; using System.Runtime.Remoting.Messaging; using System.Runtime.Remoting.Metadata; using System.Security; using System.Security.Permissions; using System.Globalization; namespace System.Runtime.Remoting.Channels { // // CLIENT-SIDE BINARY FORMATTER SINKS // public class BinaryClientFormatterSinkProvider : IClientFormatterSinkProvider { private IClientChannelSinkProvider _next; // settings from config private bool _includeVersioning = true; private bool _strictBinding = false; public BinaryClientFormatterSinkProvider() { } // BinaryClientFormatterSinkProvider public BinaryClientFormatterSinkProvider(IDictionary properties, ICollection providerData) { // look at properties if (properties != null) { foreach (DictionaryEntry entry in properties) { String keyStr = entry.Key.ToString(); switch (keyStr) { case "includeVersions": _includeVersioning = Convert.ToBoolean(entry.Value, CultureInfo.InvariantCulture); break; case "strictBinding": _strictBinding = Convert.ToBoolean(entry.Value, CultureInfo.InvariantCulture); break; default: break; } } } // not expecting any provider data CoreChannel.VerifyNoProviderData(this.GetType().Name, providerData); } // BinaryClientFormatterSinkProvider [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public IClientChannelSink CreateSink(IChannelSender channel, String url, Object remoteChannelData) { IClientChannelSink nextSink = null; if (_next != null) { nextSink = _next.CreateSink(channel, url, remoteChannelData); if (nextSink == null) return null; } SinkChannelProtocol protocol = CoreChannel.DetermineChannelProtocol(channel); BinaryClientFormatterSink sink = new BinaryClientFormatterSink(nextSink); sink.IncludeVersioning = _includeVersioning; sink.StrictBinding = _strictBinding; sink.ChannelProtocol = protocol; return sink; } // CreateSink public IClientChannelSinkProvider Next { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { return _next; } [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] set { _next = value; } } } // class BinaryClientFormatterSinkProvider public class BinaryClientFormatterSink : IClientFormatterSink { private IClientChannelSink _nextSink = null; private bool _includeVersioning = true; // should versioning be used private bool _strictBinding = false; // strict binding should be used private SinkChannelProtocol _channelProtocol = SinkChannelProtocol.Other; public BinaryClientFormatterSink(IClientChannelSink nextSink) { _nextSink = nextSink; } // BinaryClientFormatterSink internal bool IncludeVersioning { set { _includeVersioning = value; } } // IncludeVersioning internal bool StrictBinding { set { _strictBinding = value; } } // StrictBinding internal SinkChannelProtocol ChannelProtocol { set { _channelProtocol = value; } } // ChannelProtocol public IMessageSink NextSink { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { throw new NotSupportedException(); } } [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public IMessage SyncProcessMessage(IMessage msg) { IMethodCallMessage mcm = msg as IMethodCallMessage; IMessage retMsg; try { // serialize message ITransportHeaders headers; Stream requestStream; SerializeMessage(msg, out headers, out requestStream); // process message Stream returnStream; ITransportHeaders returnHeaders; _nextSink.ProcessMessage(msg, headers, requestStream, out returnHeaders, out returnStream); if (returnHeaders == null) throw new ArgumentNullException("returnHeaders"); // deserialize stream retMsg = DeserializeMessage(mcm, returnHeaders, returnStream); } catch (Exception e) { retMsg = new ReturnMessage(e, mcm); } return retMsg; } // SyncProcessMessage [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public IMessageCtrl AsyncProcessMessage(IMessage msg, IMessageSink replySink) { IMethodCallMessage mcm = (IMethodCallMessage)msg; IMessage retMsg; try { // serialize message ITransportHeaders headers; Stream requestStream; SerializeMessage(msg, out headers, out requestStream); // process message ClientChannelSinkStack sinkStack = new ClientChannelSinkStack(replySink); sinkStack.Push(this, msg); _nextSink.AsyncProcessRequest(sinkStack, msg, headers, requestStream); } catch (Exception e) { retMsg = new ReturnMessage(e, mcm); if (replySink != null) replySink.SyncProcessMessage(retMsg); } return null; } // AsyncProcessMessage // helper function to serialize the message private void SerializeMessage(IMessage msg, out ITransportHeaders headers, out Stream stream) { BaseTransportHeaders requestHeaders = new BaseTransportHeaders(); headers = requestHeaders; // add other http soap headers requestHeaders.ContentType = CoreChannel.BinaryMimeType; if (_channelProtocol == SinkChannelProtocol.Http) headers["__RequestVerb"] = "POST"; bool bMemStream = false; stream = _nextSink.GetRequestStream(msg, headers); if (stream == null) { stream = new ChunkedMemoryStream(CoreChannel.BufferPool); bMemStream = true; } CoreChannel.SerializeBinaryMessage(msg, stream, _includeVersioning); if (bMemStream) stream.Position = 0; } // SerializeMessage // helper function to deserialize the message private IMessage DeserializeMessage(IMethodCallMessage mcm, ITransportHeaders headers, Stream stream) { // deserialize the message IMessage retMsg = CoreChannel.DeserializeBinaryResponseMessage(stream, mcm, _strictBinding); stream.Close(); return retMsg; } // DeserializeMessage // // IClientChannelSink implementation // [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public void ProcessMessage(IMessage msg, ITransportHeaders requestHeaders, Stream requestStream, out ITransportHeaders responseHeaders, out Stream responseStream) { // should never gets called, since this sink is always first throw new NotSupportedException(); } // ProcessMessage [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public void AsyncProcessRequest(IClientChannelSinkStack sinkStack, IMessage msg, ITransportHeaders headers, Stream stream) { // should never be called, this sink is always first throw new NotSupportedException(); } // AsyncProcessRequest [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public void AsyncProcessResponse(IClientResponseChannelSinkStack sinkStack, Object state, ITransportHeaders headers, Stream stream) { // previously we stored the outgoing message in state IMethodCallMessage mcm = (IMethodCallMessage)state; IMessage retMsg = DeserializeMessage(mcm, headers, stream); sinkStack.DispatchReplyMessage(retMsg); } // AsyncProcessRequest [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public Stream GetRequestStream(IMessage msg, ITransportHeaders headers) { // never called on formatter sender sink throw new NotSupportedException(); } public IClientChannelSink NextChannelSink { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { return _nextSink; } } public IDictionary Properties { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { return null; } } // Properties // // end of IClientChannelSink implementation // } // class BinaryClientFormatterSink // // SERVER-SIDE SOAP FORMATTER SINKS // public class BinaryServerFormatterSinkProvider : IServerFormatterSinkProvider { private IServerChannelSinkProvider _next = null; // settings from config private bool _includeVersioning = true; private bool _strictBinding = false; private TypeFilterLevel _formatterSecurityLevel = TypeFilterLevel.Low; public BinaryServerFormatterSinkProvider() { } // BinaryServerFormatterSinkProvider public BinaryServerFormatterSinkProvider(IDictionary properties, ICollection providerData) { // look at properties if (properties != null) { foreach (DictionaryEntry entry in properties) { String keyStr = entry.Key.ToString(); switch (keyStr) { case "includeVersions": _includeVersioning = Convert.ToBoolean(entry.Value, CultureInfo.InvariantCulture); break; case "strictBinding": _strictBinding = Convert.ToBoolean(entry.Value, CultureInfo.InvariantCulture); break; case "typeFilterLevel": _formatterSecurityLevel = (TypeFilterLevel) Enum.Parse(typeof(TypeFilterLevel), (string)entry.Value); break; default: break; } } } // not expecting any provider data CoreChannel.VerifyNoProviderData(this.GetType().Name, providerData); } // BinaryServerFormatterSinkProvider [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public void GetChannelData(IChannelDataStore channelData) { } // GetChannelData [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public IServerChannelSink CreateSink(IChannelReceiver channel) { if(null == channel) { throw new ArgumentNullException("channel"); } IServerChannelSink nextSink = null; if (_next != null) nextSink = _next.CreateSink(channel); BinaryServerFormatterSink.Protocol protocol = BinaryServerFormatterSink.Protocol.Other; // see if this is an http channel String uri = channel.GetUrlsForUri("")[0]; if (String.Compare("http", 0, uri, 0, 4, StringComparison.OrdinalIgnoreCase) == 0) protocol = BinaryServerFormatterSink.Protocol.Http; BinaryServerFormatterSink sink = new BinaryServerFormatterSink(protocol, nextSink, channel); sink.TypeFilterLevel = _formatterSecurityLevel; sink.IncludeVersioning = _includeVersioning; sink.StrictBinding = _strictBinding; return sink; } // CreateSink public IServerChannelSinkProvider Next { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { return _next; } [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] set { _next = value; } } // Next [System.Runtime.InteropServices.ComVisible(false)] public TypeFilterLevel TypeFilterLevel { get { return _formatterSecurityLevel; } set { _formatterSecurityLevel = value; } } } // class BinaryServerFormatterSinkProvider public class BinaryServerFormatterSink : IServerChannelSink { [Serializable] public enum Protocol { Http, // special processing needed for http Other } private IServerChannelSink _nextSink; // If this sink doesn't recognize, the incoming // format then it should call the next // sink if there is one. private Protocol _protocol; // remembers which protocol is being used private IChannelReceiver _receiver; // transport sink used to parse url private bool _includeVersioning = true; // should versioning be used private bool _strictBinding = false; // strict binding should be used private TypeFilterLevel _formatterSecurityLevel = TypeFilterLevel.Full; private string lastUri = null; public BinaryServerFormatterSink(Protocol protocol, IServerChannelSink nextSink, IChannelReceiver receiver) { if (receiver == null) throw new ArgumentNullException("receiver"); _nextSink = nextSink; _protocol = protocol; _receiver = receiver; } // BinaryServerFormatterSinkProvider internal bool IncludeVersioning { set { _includeVersioning = value; } } // IncludeVersioning internal bool StrictBinding { set { _strictBinding = value; } } // StrictBinding [System.Runtime.InteropServices.ComVisible(false)] public TypeFilterLevel TypeFilterLevel { get { return _formatterSecurityLevel; } set { _formatterSecurityLevel = value; } } [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public ServerProcessing ProcessMessage(IServerChannelSinkStack sinkStack, IMessage requestMsg, ITransportHeaders requestHeaders, Stream requestStream, out IMessage responseMsg, out ITransportHeaders responseHeaders, out Stream responseStream) { if (requestMsg != null) { // The message has already been deserialized so delegate to the next sink. return _nextSink.ProcessMessage( sinkStack, requestMsg, requestHeaders, requestStream, out responseMsg, out responseHeaders, out responseStream); } if (requestHeaders == null) throw new ArgumentNullException("requestHeaders"); BaseTransportHeaders wkRequestHeaders = requestHeaders as BaseTransportHeaders; ServerProcessing processing; responseHeaders = null; responseStream = null; String verb = null; String contentType = null; bool bCanServiceRequest = true; // determine the content type String contentTypeHeader = null; if (wkRequestHeaders != null) contentTypeHeader = wkRequestHeaders.ContentType; else contentTypeHeader = requestHeaders["Content-Type"] as String; if (contentTypeHeader != null) { String charsetValue; HttpChannelHelper.ParseContentType(contentTypeHeader, out contentType, out charsetValue); } // check to see if Content-Type matches if ((contentType != null) && (String.CompareOrdinal(contentType, CoreChannel.BinaryMimeType) != 0)) { bCanServiceRequest = false; } // check for http specific verbs if (_protocol == Protocol.Http) { verb = (String)requestHeaders["__RequestVerb"]; if (!verb.Equals("POST") && !verb.Equals("M-POST")) bCanServiceRequest = false; } // either delegate or return an error message if we can't service the request if (!bCanServiceRequest) { // delegate to next sink if available if (_nextSink != null) { return _nextSink.ProcessMessage(sinkStack, null, requestHeaders, requestStream, out responseMsg, out responseHeaders, out responseStream); } else { // send back an error message if (_protocol == Protocol.Http) { // return a client bad request error responseHeaders = new TransportHeaders(); responseHeaders["__HttpStatusCode"] = "400"; responseHeaders["__HttpReasonPhrase"] = "Bad Request"; responseStream = null; responseMsg = null; return ServerProcessing.Complete; } else { // The transport sink will catch this and do something here. throw new RemotingException( CoreChannel.GetResourceString("Remoting_Channels_InvalidRequestFormat")); } } } try { String objectUri = null; bool bIsCustomErrorEnabled = true; object oIsCustomErrorEnabled = requestHeaders["__CustomErrorsEnabled"]; if (oIsCustomErrorEnabled != null && oIsCustomErrorEnabled is bool){ bIsCustomErrorEnabled = (bool)oIsCustomErrorEnabled; } CallContext.SetData("__CustomErrorsEnabled", bIsCustomErrorEnabled); if (wkRequestHeaders != null) objectUri = wkRequestHeaders.RequestUri; else objectUri = (String)requestHeaders[CommonTransportKeys.RequestUri]; if (objectUri != lastUri && RemotingServices.GetServerTypeForUri(objectUri) == null) throw new RemotingException( CoreChannel.GetResourceString("Remoting_ChnlSink_UriNotPublished")); else lastUri = objectUri; PermissionSet currentPermissionSet = null; if (this.TypeFilterLevel != TypeFilterLevel.Full) { currentPermissionSet = new PermissionSet(PermissionState.None); currentPermissionSet.SetPermission(new SecurityPermission(SecurityPermissionFlag.SerializationFormatter)); } try { if (currentPermissionSet != null) currentPermissionSet.PermitOnly(); // Deserialize Request - Stream to IMessage requestMsg = CoreChannel.DeserializeBinaryRequestMessage(objectUri, requestStream, _strictBinding, this.TypeFilterLevel); } finally { if (currentPermissionSet != null) CodeAccessPermission.RevertPermitOnly(); } requestStream.Close(); if(requestMsg == null) { throw new RemotingException(CoreChannel.GetResourceString("Remoting_DeserializeMessage")); } // Dispatch Call sinkStack.Push(this, null); processing = _nextSink.ProcessMessage(sinkStack, requestMsg, requestHeaders, null, out responseMsg, out responseHeaders, out responseStream); // make sure that responseStream is null if (responseStream != null) { throw new RemotingException( CoreChannel.GetResourceString("Remoting_ChnlSink_WantNullResponseStream")); } switch (processing) { case ServerProcessing.Complete: { if (responseMsg == null) throw new RemotingException(CoreChannel.GetResourceString("Remoting_DispatchMessage")); sinkStack.Pop(this); SerializeResponse(sinkStack, responseMsg, ref responseHeaders, out responseStream); break; } // case ServerProcessing.Complete case ServerProcessing.OneWay: { sinkStack.Pop(this); break; } // case ServerProcessing.OneWay: case ServerProcessing.Async: { sinkStack.Store(this, null); break; } // case ServerProcessing.Async } // switch (processing) } catch(Exception e) { processing = ServerProcessing.Complete; responseMsg = new ReturnMessage(e, (IMethodCallMessage)(requestMsg==null?new ErrorMessage():requestMsg)); // CallContext.SetData("__ClientIsClr", true); responseStream = (MemoryStream)CoreChannel.SerializeBinaryMessage(responseMsg, _includeVersioning); CallContext.FreeNamedDataSlot("__ClientIsClr"); responseStream.Position = 0; responseHeaders = new TransportHeaders(); if (_protocol == Protocol.Http) { responseHeaders["Content-Type"] = CoreChannel.BinaryMimeType; } } finally{ CallContext.FreeNamedDataSlot("__CustomErrorsEnabled"); } return processing; } // ProcessMessage [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public void AsyncProcessResponse(IServerResponseChannelSinkStack sinkStack, Object state, IMessage msg, ITransportHeaders headers, Stream stream) { SerializeResponse(sinkStack, msg, ref headers, out stream); sinkStack.AsyncProcessResponse(msg, headers, stream); } // AsyncProcessResponse [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] private void SerializeResponse(IServerResponseChannelSinkStack sinkStack, IMessage msg, ref ITransportHeaders headers, out Stream stream) { BaseTransportHeaders responseHeaders = new BaseTransportHeaders(); if (headers != null) { // copy old headers into new headers foreach (DictionaryEntry entry in headers) { responseHeaders[entry.Key] = entry.Value; } } headers = responseHeaders; if (_protocol == Protocol.Http) { responseHeaders.ContentType = CoreChannel.BinaryMimeType; } bool bMemStream = false; stream = sinkStack.GetResponseStream(msg, headers); if (stream == null) { stream = new ChunkedMemoryStream(CoreChannel.BufferPool); bMemStream = true; } bool bBashUrl = CoreChannel.SetupUrlBashingForIisSslIfNecessary(); try { CallContext.SetData("__ClientIsClr", true); CoreChannel.SerializeBinaryMessage(msg, stream, _includeVersioning); } finally { CallContext.FreeNamedDataSlot("__ClientIsClr"); CoreChannel.CleanupUrlBashingForIisSslIfNecessary(bBashUrl); } if (bMemStream) stream.Position = 0; } // SerializeResponse [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] public Stream GetResponseStream(IServerResponseChannelSinkStack sinkStack, Object state, IMessage msg, ITransportHeaders headers) { // This should never get called since we're the last in the chain, and never // push ourselves to the sink stack. throw new NotSupportedException(); } // GetResponseStream public IServerChannelSink NextChannelSink { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { return _nextSink; } } public IDictionary Properties { [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.Infrastructure, Infrastructure=true)] get { return null; } } // Properties } // class BinaryServerFormatterSink } // namespace System.Runtime.Remoting.Channnels // 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
- MenuItemCollection.cs
- TextElementCollection.cs
- WriterOutput.cs
- InheritanceRules.cs
- URLString.cs
- PathStreamGeometryContext.cs
- TemplateBindingExpressionConverter.cs
- DataGridCellEditEndingEventArgs.cs
- ContainerFilterService.cs
- UInt64Storage.cs
- SQLDateTimeStorage.cs
- RegexCharClass.cs
- HttpVersion.cs
- TreeViewEvent.cs
- XmlSchemaAttributeGroup.cs
- WindowsFormsHelpers.cs
- ChoiceConverter.cs
- MediaElementAutomationPeer.cs
- SignedPkcs7.cs
- DataGridTableStyleMappingNameEditor.cs
- MultidimensionalArrayItemReference.cs
- PackWebResponse.cs
- DataGridItemEventArgs.cs
- TreeIterator.cs
- BinaryFormatter.cs
- Crc32Helper.cs
- DecimalAnimation.cs
- XmlJsonReader.cs
- DataSourceView.cs
- ResumeStoryboard.cs
- XmlSchemaComplexContentRestriction.cs
- DragDropManager.cs
- MexHttpsBindingCollectionElement.cs
- SHA1Managed.cs
- HtmlGenericControl.cs
- CryptoApi.cs
- XmlSerializerVersionAttribute.cs
- FocusWithinProperty.cs
- StaticExtensionConverter.cs
- WinCategoryAttribute.cs
- DataBoundControlHelper.cs
- ProviderIncompatibleException.cs
- RestHandler.cs
- ProcessStartInfo.cs
- MdiWindowListItemConverter.cs
- TextBounds.cs
- OdbcDataAdapter.cs
- NavigationHelper.cs
- DataReceivedEventArgs.cs
- ClientRolePrincipal.cs
- Assembly.cs
- FixedTextView.cs
- NotFiniteNumberException.cs
- BindingBase.cs
- SchemaMapping.cs
- SqlRewriteScalarSubqueries.cs
- CultureInfo.cs
- FreeFormDragDropManager.cs
- IncrementalCompileAnalyzer.cs
- SqlInternalConnectionTds.cs
- SimpleBitVector32.cs
- IntSecurity.cs
- DataGridDetailsPresenter.cs
- VectorCollectionConverter.cs
- PeerNameRecordCollection.cs
- ManipulationVelocities.cs
- SessionEndingEventArgs.cs
- BinarySecretSecurityToken.cs
- MembershipSection.cs
- AffineTransform3D.cs
- MatrixTransform3D.cs
- SynchronizedDispatch.cs
- PostBackOptions.cs
- HMACSHA512.cs
- SemaphoreFullException.cs
- SessionViewState.cs
- ReadOnlyDictionary.cs
- UIntPtr.cs
- GridViewCommandEventArgs.cs
- Hex.cs
- ComponentChangingEvent.cs
- PropertyOverridesTypeEditor.cs
- StartUpEventArgs.cs
- ConfigXmlAttribute.cs
- CustomCategoryAttribute.cs
- TaskSchedulerException.cs
- ChannelManager.cs
- streamingZipPartStream.cs
- HandoffBehavior.cs
- Identity.cs
- AuditLogLocation.cs
- UiaCoreApi.cs
- SamlAuthorizationDecisionClaimResource.cs
- SqlDependencyUtils.cs
- MailMessage.cs
- HttpProtocolImporter.cs
- TableLayoutCellPaintEventArgs.cs
- AssemblySettingAttributes.cs
- DesignTableCollection.cs
- ManifestSignatureInformation.cs