diff --git a/mcs/class/System.ServiceModel/ChangeLog b/mcs/class/System.ServiceModel/ChangeLog index ca2229d61c99a..f8f027a61e405 100755 --- a/mcs/class/System.ServiceModel/ChangeLog +++ b/mcs/class/System.ServiceModel/ChangeLog @@ -1,3 +1,55 @@ +2010-02-05 Astushi Enomoto + + * Dummy_2_1.cs : remove AuthenticationSchemes. It blocks MT support. + +2010-02-04 Astushi Enomoto + + * Dummy.cs, net_2_1_raw_System.ServiceModel.dll.sources : add some + classes out of dummy, for monotouch (hidden in 2.1 profile). + +2010-02-04 Astushi Enomoto + + * HTTP_listener_notes.txt: Fixed some wrong description, simplified + some, and updated some. + +2010-02-04 Astushi Enomoto + + * HTTP_listener_notes.txt: some notes updated. + +2010-02-03 Astushi Enomoto + + * HTTP_listener_notes.txt: I couldn't help but write about it to + not keep myself confused by this complicated stuff. + +2010-01-20 Astushi Enomoto + + * System.ServiceModel_test.dll.sources: move back some FeatureBased + tests. + +2010-01-18 Astushi Enomoto + + * System.ServiceModel.dll.sources : added new security version types. + +2010-01-15 Astushi Enomoto + + * System.ServiceModel.dll.sources: add SL config loader here + for easy debugging under 2.0 profile. + +2010-01-13 Astushi Enomoto + + * net_2_1_raw_System.ServiceModel.dll.sources : + add EndpointAddressBuilder.cs. + +2010-01-13 Astushi Enomoto + + * net_2_1_raw_System.ServiceModel.dll.sources : + add FaultContractInfo.cs. + +2010-01-13 Astushi Enomoto + + * net_2_1_raw_System.ServiceModel.dll.sources : + add HttpCookieContainerBindingElement.cs. + 2010-01-07 Astushi Enomoto * System.ServiceModel_test.dll.sources : ended up to remove diff --git a/mcs/class/System.ServiceModel/Dummy_2_1.cs b/mcs/class/System.ServiceModel/Dummy_2_1.cs index 0be15540a7721..a3aa98d78e4c5 100644 --- a/mcs/class/System.ServiceModel/Dummy_2_1.cs +++ b/mcs/class/System.ServiceModel/Dummy_2_1.cs @@ -22,8 +22,6 @@ public interface IPolicyExportExtension {} public interface IPolicyImportExtension {} public interface IWsdlExportExtension {} public interface IWsdlImportExtension {} - public interface IEndpointBehavior {} - public interface IOperationBehavior {} public interface IContractBehavior {} } namespace System.ServiceModel.Dispatcher @@ -33,10 +31,6 @@ namespace System.ServiceModel.Security { class Dummy {} } -namespace System.Net -{ - public enum AuthenticationSchemes {Anonymous} -} namespace System.Net.Security { public enum ProtectionLevel {None} diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AddressHeader.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AddressHeader.cs index ebaeaebc06fb1..4372574e1ee68 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AddressHeader.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AddressHeader.cs @@ -1,9 +1,11 @@ // // System.ServiceModel.AddressHeader.cs // -// Author: Duncan Mak (duncan@novell.com) +// Authors: +// Duncan Mak (duncan@novell.com) +// Atsushi Enomoto (atsushi@ximian.com) // -// Copyright (C) 2005 Novell, Inc (http://www.novell.com) +// Copyright (C) 2005,2010 Novell, Inc (http://www.novell.com) // // Permission is hereby granted, free of charge, to any person obtaining // a copy of this software and associated documentation files (the @@ -26,9 +28,11 @@ // using System; +using System.IO; using System.Runtime.Serialization; using System.ServiceModel; using System.Xml; +using System.Xml.Schema; namespace System.ServiceModel.Channels { @@ -69,10 +73,14 @@ public override bool Equals (object obj) return o.Name == this.Name && o.Namespace == this.Namespace; } - [MonoTODO] public virtual XmlDictionaryReader GetAddressHeaderReader () { - throw new NotImplementedException (); + var sw = new StringWriter (); + var s = new XmlWriterSettings () { OmitXmlDeclaration = true }; + var xw = XmlDictionaryWriter.CreateDictionaryWriter (XmlWriter.Create (sw, s)); + WriteAddressHeader (xw); + xw.Close (); + return XmlDictionaryReader.CreateDictionaryReader (XmlReader.Create (new StringReader (sw.ToString ()))); } public override int GetHashCode () @@ -87,7 +95,7 @@ public T GetValue () public T GetValue (XmlObjectSerializer formatter) { - throw new NotImplementedException (); + return (T) formatter.ReadObject (GetAddressHeaderReader ()); } protected abstract void OnWriteAddressHeaderContents (XmlDictionaryWriter writer); @@ -151,12 +159,8 @@ internal DefaultAddressHeader (string name, string ns, object value) internal DefaultAddressHeader (string name, string ns, object value, XmlObjectSerializer formatter) { - if (formatter == null) { - if (value == null) - formatter = new NetDataContractSerializer (); - else - formatter = new DataContractSerializer (value.GetType ()); - } + if (formatter == null) + formatter = value != null ? new DataContractSerializer (value.GetType ()) : null; this.name = name; this.ns = ns; this.formatter = formatter; @@ -173,7 +177,10 @@ internal DefaultAddressHeader (string name, string ns, object value, XmlObjectSe protected override void OnWriteAddressHeaderContents (XmlDictionaryWriter writer) { - this.formatter.WriteObject (writer, value); + if (value == null) + writer.WriteAttributeString ("i", "nil", "http://www.w3.org/2001/XMLSchema-instance", "true"); + else + this.formatter.WriteObject (writer, value); } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AspNetReplyChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AspNetReplyChannel.cs index e859f31063c7b..2dd63b7984f89 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AspNetReplyChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/AspNetReplyChannel.cs @@ -150,7 +150,6 @@ public override bool WaitForRequest (TimeSpan timeout) public override bool WaitForRequest (TimeSpan timeout) { -Console.WriteLine ("Enter AspNetReplyChannel.WaitForRequest"); if (wait != null) throw new InvalidOperationException ("Another wait operation is in progress"); try { @@ -158,7 +157,6 @@ public override bool WaitForRequest (TimeSpan timeout) listener.ListenerManager.GetHttpContextAsync (timeout, HttpContextAcquired); if (wait != null) // in case callback is done before WaitOne() here. return wait.WaitOne (timeout, false); -Console.WriteLine ("Exit AspNetReplyChannel.WaitForRequest"); return waiting.Count > 0; } finally { wait = null; @@ -167,7 +165,6 @@ public override bool WaitForRequest (TimeSpan timeout) void HttpContextAcquired (HttpContextInfo ctx) { -Console.WriteLine ("Enter HttpContextAcquired: {0}", ctx != null ? ctx.RequestUrl : null); if (wait == null) throw new InvalidOperationException ("WaitForRequest operation has not started"); var sctx = (AspNetHttpContextInfo) ctx; @@ -176,7 +173,6 @@ void HttpContextAcquired (HttpContextInfo ctx) var wait_ = wait; wait = null; wait_.Set (); -Console.WriteLine ("Exit HttpContextAcquired: {0}", ctx != null ? ctx.RequestUrl : null); } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChangeLog b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChangeLog index 9435288bd324e..e19c0041c3afb 100755 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChangeLog +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChangeLog @@ -1,3 +1,111 @@ +2010-02-05 Atsushi Enomoto + + * HttpRequestChannel.cs, HttpTransportBindingElement.cs : + enable authentication schemes on monotouch. + +2010-02-04 Atsushi Enomoto + + * SvcHttpHandler.cs : a wait handle could be used for more than one + requests and hence it sometimes blocked one reply channel. Now + it creates a wait handle for each ASP.NET request so that such + multiple use should not occur. This should fix blocking on + concurrent requests (it indeed fixes as long as I can see). + +2010-02-04 Atsushi Enomoto + + * AspNetReplyChannel.cs : remove garbage output. + +2010-02-04 Atsushi Enomoto + + * SvcHttpHandler.cs : Use lock when it tries to create the service + host. + +2010-02-02 Atsushi Enomoto + + * SvcHttpHandlerFactory.cs : lock when it tries to acquire + HttpHandler. + +2010-02-02 Atsushi Enomoto + + * HttpListenerManager.cs : add another workaround for blocking + concurrent calls. + +2010-02-02 Atsushi Enomoto + + * HttpListenerManager.cs : small refactoring. + +2010-01-22 Atsushi Enomoto + + * TcpDuplexSessionChannel.cs : added a workaround receiver delay + that somehow makes callback client to not cause infinite loop. + +2010-01-22 Atsushi Enomoto + + * TcpDuplexSessionChannel.cs, PeerDuplexChannel.cs, + DuplexChannelBase.cs : Receive() should rather use TryReceive(). + It should not be in reverse order. + +2010-01-22 Atsushi Enomoto + + * HttpReplyChannel.cs, HttpListenerManager.cs : + Implement async cancellation in the expected manner (though with + some hack). This mostly removed nunit blockers. + +2010-01-22 Atsushi Enomoto + + * CommunicationObject.cs : fix wrong status changes. + +2010-01-20 Atsushi Enomoto + + * AddressHeader.cs : XmlSchema.InstanceNamespace didn't exist in 2.1 :( + +2010-01-20 Atsushi Enomoto + + * AddressHeader.cs : implement remaining bits. + Eliminate dependency on NetDataContractSerializer. + +2010-01-20 Atsushi Enomoto + + * CommunicationObject.cs : in Fault(), do similar work as previous + change does. + +2010-01-19 Atsushi Enomoto + + * CommunicationObject.cs : when process state changes, lock the + object to make sure the state transition is valid. + Change OnClosed/OnClosing to do the way OnOpened/OnOpening does. + +2010-01-13 Atsushi Enomoto + + * MessageHeaders.cs : implement SetAction(). + +2010-01-13 Atsushi Enomoto + + * ChannelFactoryBase.cs : fix build. + +2010-01-13 Atsushi Enomoto + + * ChannelBase.cs : cosmetic API fix for SL3. + +2010-01-13 Atsushi Enomoto + + * ChannelFactoryBase.cs : + implement On{Begin/End}Close() on the generic type. + +2010-01-13 Atsushi Enomoto + + * HttpChannelFactory.cs, TcpChannelFactory.cs, + ChannelFactoryBase.cs, NamedPipeChannelFactory.cs + PeerChannelFactory.cs, HttpRequestChannel.cs: + fix ChannelFactoryBase API; move On(Begin/End)Open() to internal + type and made required changes. + +2010-01-13 Atsushi Enomoto + + * HttpCookieContainerBindingElement.cs : new. + * IHttpCookieContainer.cs : fix type name. + * HttpRequestChannel.cs, HttpChannelFactory.cs : support above. + 2010-01-07 Atsushi Enomoto * TcpBinaryFrameManager.cs : treat EOF as interrupted stream too (it diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelBase.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelBase.cs index 693799434b3a8..a890d0632a672 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelBase.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelBase.cs @@ -69,10 +69,12 @@ protected ChannelBase (ChannelManagerBase manager) return null; } +#if !NET_2_1 protected override void OnClosed () { base.OnClosed (); } +#endif TimeSpan IDefaultCommunicationTimeouts.CloseTimeout { get { return DefaultCloseTimeout; } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelFactoryBase.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelFactoryBase.cs index 98e398434c73d..3460963125631 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelFactoryBase.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/ChannelFactoryBase.cs @@ -38,10 +38,31 @@ internal abstract class TransportChannelFactoryBase : ChannelFactoryBa { protected TransportChannelFactoryBase (TransportBindingElement source, BindingContext ctx) { - Source = source; + Transport = source; } - public TransportBindingElement Source { get; private set; } + public TransportBindingElement Transport { get; private set; } + + Action open_delegate; + + protected override IAsyncResult OnBeginOpen (TimeSpan timeout, + AsyncCallback callback, object state) + { + if (open_delegate == null) + open_delegate = new Action (OnOpen); + return open_delegate.BeginInvoke (timeout, callback, state); + } + + protected override void OnEndOpen (IAsyncResult result) + { + if (open_delegate == null) + throw new InvalidOperationException ("Async open operation has not started"); + open_delegate.EndInvoke (result); + } + + protected override void OnOpen (TimeSpan timeout) + { + } } public abstract class ChannelFactoryBase @@ -97,6 +118,19 @@ protected override void OnClose (TimeSpan timeout) base.OnClose (timeout - (DateTime.Now - start)); } + protected override IAsyncResult OnBeginClose (TimeSpan timeout, AsyncCallback callback, object state) + { + // base impl. will call this.OnClose() + // FIXME: use async BeginClose/EndClose on the channels. + return base.OnBeginClose (timeout, callback, state); + } + + protected override void OnEndClose (IAsyncResult result) + { + // base impl. will call this.OnClose() + base.OnEndClose (result); + } + protected void ValidateCreateChannel () { ThrowIfDisposedOrNotOpen (); @@ -150,28 +184,6 @@ protected override void OnAbort () // what should we do here? } - Action open_delegate; - - protected override IAsyncResult OnBeginOpen (TimeSpan timeout, - AsyncCallback callback, object state) - { - if (open_delegate == null) - open_delegate = new Action (OnOpen); - return open_delegate.BeginInvoke (timeout, callback, state); - } - - protected override void OnEndOpen (IAsyncResult result) - { - if (open_delegate == null) - throw new InvalidOperationException ("Async open operation has not started"); - open_delegate.EndInvoke (result); - } - - protected override void OnOpen (TimeSpan timeout) - { - // what should we do here? - } - Action close_delegate; protected override IAsyncResult OnBeginClose (TimeSpan timeout, AsyncCallback callback, object state) diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/CommunicationObject.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/CommunicationObject.cs index 56b14447670c2..88a186400749a 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/CommunicationObject.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/CommunicationObject.cs @@ -26,6 +26,7 @@ // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. // using System; +using System.Reflection; using System.ServiceModel; using System.Threading; @@ -36,7 +37,7 @@ public abstract class CommunicationObject : ICommunicationObject object mutex; CommunicationState state = CommunicationState.Created; TimeSpan default_open_timeout = TimeSpan.FromMinutes (1), default_close_timeout = TimeSpan.FromMinutes (1); - bool aborted, on_closed_called; + bool aborted; protected CommunicationObject () : this (new object ()) @@ -92,11 +93,9 @@ public void Abort () } } - [MonoTODO] protected void Fault () { - state = CommunicationState.Faulted; - OnFaulted (); + ProcessFaulted (); } public IAsyncResult BeginClose (AsyncCallback callback, @@ -184,14 +183,20 @@ public void Open (TimeSpan timeout) void ProcessClosing () { - if (State == CommunicationState.Faulted) - throw new CommunicationObjectFaultedException (); - state = CommunicationState.Closing; - OnClosing (); + lock (ThisLock) { + if (State == CommunicationState.Faulted) + throw new CommunicationObjectFaultedException (); + OnClosing (); + if (state != CommunicationState.Closing) { + state = CommunicationState.Faulted; + throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnClosing method that does not call base OnClosing method (declared in {1} type).", this.GetType (), GetType ().GetMethod ("OnClosing", BindingFlags.NonPublic | BindingFlags.Instance).DeclaringType)); + } + } } protected virtual void OnClosing () { + state = CommunicationState.Closing; // This means, if this method is overriden, then // Opening event is surpressed. if (Closing != null) @@ -200,31 +205,46 @@ protected virtual void OnClosing () void ProcessClosed () { - state = CommunicationState.Closed; - on_closed_called = false; - OnClosed (); - if (!on_closed_called) - throw new InvalidOperationException ("OnClosed method is implemented but it did not call its base OnClosed method"); + lock (ThisLock) { + OnClosed (); + if (state != CommunicationState.Closed) { + state = CommunicationState.Faulted; + throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnClosed method that does not call base OnClosed method (declared in {1} type).", this.GetType (), GetType ().GetMethod ("OnClosed", BindingFlags.NonPublic | BindingFlags.Instance).DeclaringType)); + } + } } protected virtual void OnClosed () { + state = CommunicationState.Closed; // This means, if this method is overriden, then // Closed event is surpressed. if (Closed != null) Closed (this, new EventArgs ()); - on_closed_called = true; } protected abstract void OnEndClose (IAsyncResult result); protected abstract void OnEndOpen (IAsyncResult result); - [MonoTODO] + void ProcessFaulted () + { + lock (ThisLock) { + if (State == CommunicationState.Faulted) + throw new CommunicationObjectFaultedException (); + OnFaulted (); + if (state != CommunicationState.Faulted) { + state = CommunicationState.Faulted; // FIXME: am not sure if this makes sense ... + throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnFaulted method that does not call base OnFaulted method (declared in {1} type).", this.GetType (), GetType ().GetMethod ("OnFaulted", BindingFlags.NonPublic | BindingFlags.Instance).DeclaringType)); + } + } + } + protected virtual void OnFaulted () { + state = CommunicationState.Faulted; // This means, if this method is overriden, then - // Opened event is surpressed. + // Faulted event is surpressed. if (Faulted != null) Faulted (this, new EventArgs ()); } @@ -233,10 +253,12 @@ protected virtual void OnFaulted () void ProcessOpened () { - OnOpened (); - if (state != CommunicationState.Opened) { - throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnOpened method that does not call base OnOpened method.", this.GetType ())); - state = CommunicationState.Faulted; + lock (ThisLock) { + OnOpened (); + if (state != CommunicationState.Opened) { + state = CommunicationState.Faulted; + throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnOpened method that does not call base OnOpened method (declared in {1} type).", this.GetType (), GetType ().GetMethod ("OnOpened", BindingFlags.NonPublic | BindingFlags.Instance).DeclaringType)); + } } } @@ -249,11 +271,13 @@ protected virtual void OnOpened () void ProcessOpening () { - ThrowIfDisposedOrImmutable (); - OnOpening (); - if (state != CommunicationState.Opening) { - throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnOpening method that does not call base OnOpening method.", this.GetType ())); - state = CommunicationState.Faulted; + lock (ThisLock) { + ThrowIfDisposedOrImmutable (); + OnOpening (); + if (state != CommunicationState.Opening) { + state = CommunicationState.Faulted; + throw new InvalidOperationException (String.Format ("Communication object {0} has an overriden OnOpening method that does not call base OnOpening method (declared in {1} type).", this.GetType (), GetType ().GetMethod ("OnOpening", BindingFlags.NonPublic | BindingFlags.Instance).DeclaringType)); + } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/DuplexChannelBase.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/DuplexChannelBase.cs index 75149f816f4a7..f38c6382e0c3d 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/DuplexChannelBase.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/DuplexChannelBase.cs @@ -166,7 +166,13 @@ public virtual Message Receive () return Receive (this.DefaultReceiveTimeout); } - public abstract Message Receive (TimeSpan timeout); + public virtual Message Receive (TimeSpan timeout) + { + Message msg; + if (!TryReceive (timeout, out msg)) + throw new TimeoutException (); + return msg; + } // TryReceive @@ -184,16 +190,7 @@ public virtual bool EndTryReceive (IAsyncResult result, out Message message) return try_receive_handler.EndInvoke (out message, result); } - public virtual bool TryReceive (TimeSpan timeout, out Message message) - { - try { - message = Receive (timeout); - return true; - } catch (TimeoutException) { - message = null; - return false; - } - } + public abstract bool TryReceive (TimeSpan timeout, out Message message); // WaitForMessage diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpChannelFactory.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpChannelFactory.cs index d61bc95214870..62037978de334 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpChannelFactory.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpChannelFactory.cs @@ -40,6 +40,9 @@ internal class HttpChannelFactory : TransportChannelFactoryBase (mbe); break; } +#if NET_2_1 + var cbe = be as HttpCookieContainerBindingElement; + if (cbe != null) + cookie_manager = cbe.GetProperty (ctx); +#endif } if (encoder == null) encoder = new TextMessageEncoder (MessageVersion.Default, Encoding.UTF8); @@ -67,7 +75,7 @@ public HttpChannelFactory (HttpTransportBindingElement source, BindingContext ct { ThrowIfDisposedOrNotOpen (); - if (Source.Scheme != address.Uri.Scheme) + if (Transport.Scheme != address.Uri.Scheme) throw new ArgumentException (String.Format ("Argument EndpointAddress has unsupported URI scheme: {0}", address.Uri.Scheme)); if (MessageEncoder.MessageVersion.Addressing.Equals (AddressingVersion.None) && @@ -103,5 +111,14 @@ protected override void OnEndOpen (IAsyncResult result) protected override void OnOpen (TimeSpan timeout) { } + + public override T GetProperty () + { +#if NET_2_1 + if (cookie_manager is T) + return (T) (object) cookie_manager; +#endif + return base.GetProperty (); + } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpListenerManager.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpListenerManager.cs index 07ba90ce00b1a..88610e43d8798 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpListenerManager.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpListenerManager.cs @@ -157,7 +157,7 @@ protected override void OnUnregister (IChannelListener listener, bool abort) http_listener = null; } - public override void KickContextReceiver (IChannelListener listener, Action contextReceivedCallback) + protected override void KickContextReceiver (IChannelListener listener, Action contextReceivedCallback) { http_listener.BeginGetContext (delegate (IAsyncResult result) { var hctx = http_listener.EndGetContext (result); @@ -192,7 +192,7 @@ protected override void OnUnregister (IChannelListener listener, bool abort) Func wait_delegate; - public override void KickContextReceiver (IChannelListener listener, Action contextReceivedCallback) + protected override void KickContextReceiver (IChannelListener listener, Action contextReceivedCallback) { if (wait_delegate == null) wait_delegate = new Func (http_handler.WaitForRequest); @@ -270,6 +270,11 @@ public void Stop (bool abort) protected abstract void OnRegister (IChannelListener listener, TimeSpan timeout); protected abstract void OnUnregister (IChannelListener listener, bool abort); + public void CancelGetHttpContextAsync () + { + wait_http_ctx.Set (); + } + // Do not directly handle retrieved HttpListenerContexts when // the listener received ones. // Instead, iterate every listeners to find the most-likely- @@ -297,25 +302,32 @@ public void GetHttpContextAsync (TimeSpan timeout, Action callb } } - public abstract void KickContextReceiver (IChannelListener listener, Action contextReceiverCallback); + protected abstract void KickContextReceiver (IChannelListener listener, Action contextReceiverCallback); void DispatchHttpListenerContext (HttpContextInfo ctx) { if (wsdl_instance == null) { - pending.Add (ctx); - wait_http_ctx.Set (); + AddListenerContext (this, ctx); return; } foreach (var l in registered_channels [channel_listener.Uri]) { var lm = l.GetProperty (); if (lm.FilterHttpContext (ctx)) { - lm.pending.Add (ctx); - lm.wait_http_ctx.Set (); + AddListenerContext (lm, ctx); return; } } - pending.Add (ctx); - wait_http_ctx.Set (); + AddListenerContext (this, ctx); + } + + static void AddListenerContext (HttpListenerManager lm, HttpContextInfo ctx) + { + lock (registered_channels) { + lm.pending.Add (ctx); + // FIXME: this should not be required, but it somehow saves some failures wrt concurrent calls. + Thread.Sleep (100); + lm.wait_http_ctx.Set (); + } } const UriComponents cmpflag = UriComponents.HttpRequestUrl ^ UriComponents.Query; diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpReplyChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpReplyChannel.cs index f35245736eeda..ac253c26609d9 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpReplyChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpReplyChannel.cs @@ -50,10 +50,37 @@ public HttpSimpleReplyChannel (HttpSimpleChannelListener listener protected override void OnAbort () { + AbortConnections (TimeSpan.Zero); + base.OnAbort (); // FIXME: remove it. The base is wrong. But it is somehow required to not block some tests. + } + + public override bool CancelAsync (TimeSpan timeout) + { + AbortConnections (timeout); + // FIXME: this wait is sort of hack (because it should not be required), but without it some tests are blocked. + // This hack even had better be moved to base.CancelAsync(). + if (CurrentAsyncResult != null) + CurrentAsyncResult.AsyncWaitHandle.WaitOne (TimeSpan.FromMilliseconds (300)); + return base.CancelAsync (timeout); + } + + void SignalAsyncWait () + { + if (wait == null) + return; + var wait_ = wait; + wait = null; + wait_.Set (); + } + + void AbortConnections (TimeSpan timeout) + { + // FIXME: use timeout lock (waiting) - foreach (HttpListenerContext ctx in waiting) - ctx.Response.Abort (); - base.OnAbort (); // FIXME: remove it. The base is wrong. + foreach (var ctx in waiting) + ctx.Response.Close (); + if (wait != null) + source.ListenerManager.CancelGetHttpContextAsync (); } protected override void OnClose (TimeSpan timeout) @@ -63,9 +90,7 @@ protected override void OnClose (TimeSpan timeout) reqctx.Close (timeout); // FIXME: consider timeout - lock (waiting) - foreach (HttpListenerContext ctx in waiting) - ctx.Response.Close (); + AbortConnections (timeout - (DateTime.Now - start)); base.OnClose (timeout - (DateTime.Now - start)); } @@ -169,9 +194,7 @@ void HttpContextAcquired (HttpContextInfo ctx) var sctx = (HttpListenerContextInfo) ctx; if (State == CommunicationState.Opened && ctx != null) waiting.Add (sctx.Source); - var wait_ = wait; - wait = null; - wait_.Set (); + SignalAsyncWait (); } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpRequestChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpRequestChannel.cs index 1a5cb757b886e..8e700f3c0c3c8 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpRequestChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpRequestChannel.cs @@ -77,7 +77,7 @@ void BeginProcessRequest (HttpChannelRequestAsyncResult result) // FIXME: is distination really like this? Uri destination = message.Headers.To; if (destination == null) { - if (source.Source.ManualAddressing) + if (source.Transport.ManualAddressing) throw new InvalidOperationException ("When manual addressing is enabled on the transport, every request messages must be set its destination address."); else destination = Via ?? RemoteAddress.Uri; @@ -87,9 +87,15 @@ void BeginProcessRequest (HttpChannelRequestAsyncResult result) web_request.Method = "POST"; web_request.ContentType = Encoder.ContentType; -#if !NET_2_1 // until we support NetworkCredential like SL4 will do. +#if NET_2_1 + var cmgr = source.GetProperty (); + if (cmgr != null) + ((HttpWebRequest) web_request).CookieContainer = cmgr.CookieContainer; +#endif + +#if !NET_2_1 || MONOTOUCH // until we support NetworkCredential like SL4 will do. // client authentication (while SL3 has NetworkCredential class, it is not implemented yet. So, it is non-SL only.) - var httpbe = (HttpTransportBindingElement) source.Source; + var httpbe = (HttpTransportBindingElement) source.Transport; string authType = null; switch (httpbe.AuthenticationScheme) { // AuthenticationSchemes.Anonymous is the default, ignored. diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpTransportBindingElement.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpTransportBindingElement.cs index 9376700f0a6dd..3e9553496dced 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpTransportBindingElement.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/HttpTransportBindingElement.cs @@ -42,15 +42,17 @@ public class HttpTransportBindingElement : TransportBindingElement, unsafe_ntlm_auth; bool use_default_proxy = true, keep_alive_enabled = true; int max_buffer_size = 0x10000; - AuthenticationSchemes auth_scheme = - AuthenticationSchemes.Anonymous; - AuthenticationSchemes proxy_auth_scheme = - AuthenticationSchemes.Anonymous; HostNameComparisonMode host_cmp_mode; Uri proxy_address; string realm = String.Empty; TransferMode transfer_mode; IDefaultCommunicationTimeouts timeouts; +#if !NET_2_1 + AuthenticationSchemes auth_scheme = + AuthenticationSchemes.Anonymous; + AuthenticationSchemes proxy_auth_scheme = + AuthenticationSchemes.Anonymous; +#endif // If you add fields, do not forget them in copy constructor. public HttpTransportBindingElement () @@ -67,26 +69,35 @@ public HttpTransportBindingElement () use_default_proxy = other.use_default_proxy; keep_alive_enabled = other.keep_alive_enabled; max_buffer_size = other.max_buffer_size; - auth_scheme = other.auth_scheme; - proxy_auth_scheme = other.proxy_auth_scheme; host_cmp_mode = other.host_cmp_mode; proxy_address = other.proxy_address; realm = other.realm; transfer_mode = other.transfer_mode; // FIXME: it does not look safe timeouts = other.timeouts; +#if !NET_2_1 + auth_scheme = other.auth_scheme; + proxy_auth_scheme = other.proxy_auth_scheme; +#endif } - public bool AllowCookies { - get { return allow_cookies; } - set { allow_cookies = value; } - } - +#if !NET_2_1 public AuthenticationSchemes AuthenticationScheme { get { return auth_scheme; } set { auth_scheme = value; } } + public AuthenticationSchemes ProxyAuthenticationScheme { + get { return proxy_auth_scheme; } + set { proxy_auth_scheme = value; } + } +#endif + + public bool AllowCookies { + get { return allow_cookies; } + set { allow_cookies = value; } + } + public bool BypassProxyOnLocal { get { return bypass_proxy_on_local; } set { bypass_proxy_on_local = value; } @@ -112,11 +123,6 @@ public HttpTransportBindingElement () set { proxy_address = value; } } - public AuthenticationSchemes ProxyAuthenticationScheme { - get { return proxy_auth_scheme; } - set { proxy_auth_scheme = value; } - } - public string Realm { get { return realm; } set { realm = value; } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/IHttpCookieContainer.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/IHttpCookieContainer.cs index 00fe39d946f4f..e016772f0b504 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/IHttpCookieContainer.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/IHttpCookieContainer.cs @@ -4,7 +4,7 @@ namespace System.ServiceModel.Channels { // SL-only interface. - public interface IHttpCookieContainer + public interface IHttpCookieContainerManager { CookieContainer CookieContainer { get; set; } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/MessageHeaders.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/MessageHeaders.cs index 2cbb37bf2113f..8e022ed54e825 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/MessageHeaders.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/MessageHeaders.cs @@ -431,5 +431,13 @@ public void WriteStartHeader (int index, XmlWriter writer) public UnderstoodHeaders UnderstoodHeaders { get { throw new NotImplementedException (); } } + + public void SetAction (XmlDictionaryString action) + { + if (action == null) + Action = null; + else + Action = action.Value; + } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/NamedPipeChannelFactory.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/NamedPipeChannelFactory.cs index b36102cf72f60..41d181093e0a6 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/NamedPipeChannelFactory.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/NamedPipeChannelFactory.cs @@ -37,13 +37,14 @@ namespace System.ServiceModel.Channels { - internal class NamedPipeChannelFactory : ChannelFactoryBase + internal class NamedPipeChannelFactory : TransportChannelFactoryBase { NamedPipeTransportBindingElement source; MessageEncoder encoder; XmlDictionaryReaderQuotas quotas; public NamedPipeChannelFactory (NamedPipeTransportBindingElement source, BindingContext ctx) + : base (source, ctx) { foreach (BindingElement be in ctx.RemainingBindingElements) { MessageEncodingBindingElement mbe = be as MessageEncodingBindingElement; @@ -79,9 +80,5 @@ public NamedPipeChannelFactory (NamedPipeTransportBindingElement source, Binding throw new InvalidOperationException (String.Format ("Channel type {0} is not supported.", typeof (TChannel).Name)); } - - protected override void OnOpen (TimeSpan timeout) - { - } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerChannelFactory.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerChannelFactory.cs index 8ffc8252f86e4..f0fd8bf538e85 100755 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerChannelFactory.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerChannelFactory.cs @@ -43,12 +43,13 @@ internal interface IPeerChannelManager MessageEncoder MessageEncoder { get; } } - internal class PeerChannelFactory : ChannelFactoryBase, IPeerChannelManager + internal class PeerChannelFactory : TransportChannelFactoryBase, IPeerChannelManager { PeerTransportBindingElement source; MessageEncoder encoder; public PeerChannelFactory (PeerTransportBindingElement source, BindingContext ctx) + : base (source, ctx) { this.source = source; foreach (BindingElement be in ctx.RemainingBindingElements) { diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerDuplexChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerDuplexChannel.cs index 85207a3a2198b..21f63bb794295 100755 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerDuplexChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/PeerDuplexChannel.cs @@ -256,15 +256,18 @@ internal void EnqueueMessage (Message message) Queue queue = new Queue (); AutoResetEvent receive_handle = new AutoResetEvent (false); - public override Message Receive (TimeSpan timeout) + public override bool TryReceive (TimeSpan timeout, out Message message) { ThrowIfDisposedOrNotOpen (); DateTime start = DateTime.Now; - if (queue.Count > 0) - return queue.Dequeue (); - receive_handle.WaitOne (); - return queue.Dequeue (); + if (queue.Count > 0 || receive_handle.WaitOne (timeout)) { + message = queue.Dequeue (); + return message == null; + } else { + message = null; + return false; + } } public override bool WaitForMessage (TimeSpan timeout) diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandler.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandler.cs index 096fe015258c3..413650ba3eba8 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandler.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandler.cs @@ -45,10 +45,11 @@ internal class WcfListenerInfo public WcfListenerInfo () { Pending = new List (); + ProcessRequestHandles = new List (); } public IChannelListener Listener { get; set; } - public AutoResetEvent ProcessRequestHandle { get; set; } + public List ProcessRequestHandles { get; private set; } public List Pending { get; private set; } } @@ -62,12 +63,15 @@ protected override IChannelListener GetKeyForItem (WcfListenerInfo info) internal class SvcHttpHandler : IHttpHandler { + static object type_lock = new object (); + Type type; Type factory_type; string path; ServiceHostBase host; WcfListenerInfoCollection listeners = new WcfListenerInfoCollection (); Dictionary wcf_wait_handles = new Dictionary (); + AutoResetEvent wait_for_request_handle = new AutoResetEvent (false); int close_state; public SvcHttpHandler (Type type, Type factoryType, string path) @@ -91,8 +95,14 @@ public HttpContext WaitForRequest (IChannelListener listener) if (close_state > 0) return null; - if (listeners [listener].Pending.Count == 0) - listeners [listener].ProcessRequestHandle.WaitOne (); + var wait = new ManualResetEvent (false); + var info = listeners [listener]; + if (info.Pending.Count == 0) { + info.ProcessRequestHandles.Add (wait); + wait_for_request_handle.Set (); + wait.WaitOne (); + info.ProcessRequestHandles.Remove (wait); + } var ctx = listeners [listener].Pending [0]; listeners [listener].Pending.RemoveAt (0); @@ -145,7 +155,8 @@ public void ProcessRequest (HttpContext context) lock (i) { i.Pending.Add (context); wcf_wait_handles [context] = wait; - i.ProcessRequestHandle.Set (); + if (i.ProcessRequestHandles.Count > 0) + i.ProcessRequestHandles [0].Set (); } wait.WaitOne (); @@ -171,9 +182,8 @@ public void Close () public void RegisterListener (IChannelListener listener) { - listeners.Add (new WcfListenerInfo () { - Listener = listener, - ProcessRequestHandle = new AutoResetEvent (false) }); + lock (type_lock) + listeners.Add (new WcfListenerInfo () {Listener = listener}); } public void UnregisterListener (IChannelListener listener) @@ -183,6 +193,8 @@ public void UnregisterListener (IChannelListener listener) void EnsureServiceHost () { + lock (type_lock) { + if (host != null) return; @@ -199,6 +211,8 @@ void EnsureServiceHost () // Not precise, but it needs some wait time to have all channels start requesting. And it is somehow required. Thread.Sleep (500); + + } } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandlerFactory.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandlerFactory.cs index 928078f7dc6b6..47776b192532a 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandlerFactory.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/SvcHttpHandlerFactory.cs @@ -59,6 +59,8 @@ public static SvcHttpHandler GetHandlerForListener (IChannelListener listener) public IHttpHandler GetHandler (HttpContext context, string requestType, string url, string pathTranslated) { + lock (handlers) { + if (handlers.ContainsKey (url)) return handlers [url]; @@ -71,6 +73,8 @@ public IHttpHandler GetHandler (HttpContext context, string requestType, string handlers [url] = handler; return handler; + + } } public void ReleaseHandler (IHttpHandler handler) diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpChannelFactory.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpChannelFactory.cs index 1ea4f78ceca86..cd4cc3a262b41 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpChannelFactory.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpChannelFactory.cs @@ -35,12 +35,12 @@ public TcpChannelInfo (TransportBindingElement element, MessageEncoder encoder, public XmlDictionaryReaderQuotas ReaderQuotas { get; private set; } } - internal class TcpChannelFactory : ChannelFactoryBase + internal class TcpChannelFactory : TransportChannelFactoryBase { TcpChannelInfo info; - [MonoTODO] public TcpChannelFactory (TcpTransportBindingElement source, BindingContext ctx) + : base (source, ctx) { MessageEncoder encoder = null; XmlDictionaryReaderQuotas quotas = null; @@ -76,10 +76,5 @@ public TcpChannelFactory (TcpTransportBindingElement source, BindingContext ctx) throw new InvalidOperationException (String.Format ("Channel type {0} is not supported.", typeof (TChannel).Name)); } - - [MonoTODO] - protected override void OnOpen (TimeSpan timeout) - { - } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpDuplexSessionChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpDuplexSessionChannel.cs index 0ffcf8837e278..380dad2e6208e 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpDuplexSessionChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Channels/TcpDuplexSessionChannel.cs @@ -153,37 +153,27 @@ public override void Send (Message message, TimeSpan timeout) frame.WriteSizedMessage (message); } - public override Message Receive () - { - return Receive (DefaultReceiveTimeout); - } - - public override Message Receive (TimeSpan timeout) + public override bool TryReceive (TimeSpan timeout, out Message message) { ThrowIfDisposedOrNotOpen (); + // FIXME: there seems to be some pipeline or channel- + // recycling issues, which could be mostly workarounded + // by delaying input receiver. + // This place is not ideal, but it covers both loops in + // ChannelDispatcher and DuplexClientRuntimeChannel. + Thread.Sleep (50); + if (timeout <= TimeSpan.Zero) throw new ArgumentException (String.Format ("Timeout value must be positive value. It was {0}", timeout)); client.ReceiveTimeout = (int) timeout.TotalMilliseconds; - var ret = frame.ReadSizedMessage (); + message = frame.ReadSizedMessage (); // FIXME: this may not be precise, but connection might be reused for some weird socket state transition (that's what happens). So as a workaround, avoid closing the session by sending EndRecord from this channel at OnClose(). - if (ret == null) + if (message == null) { session = null; - return ret; - } - - public override bool TryReceive (TimeSpan timeout, out Message message) - { - try { - DateTime start = DateTime.Now; - message = Receive (timeout); - if (message != null) - return true; - return false; - } catch (TimeoutException) { - message = null; return false; } + return true; } public override bool WaitForMessage (TimeSpan timeout) diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ChangeLog b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ChangeLog index 3cd44b966f680..d8462b07f3f98 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ChangeLog +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ChangeLog @@ -1,3 +1,36 @@ +2010-02-04 Atsushi Enomoto + + * ClientCredentials.cs, ContractDescription.cs, + IEndpointBehavior.cs, IOperationBehavior.cs : add monotouch support + for client behavior. + +2010-01-28 Atsushi Enomoto + + * ServiceContractGenerator.cs : when Options.AsynchronousMethods is + specified, generate async methods *as well as* sync methods (i.e. + not exclusively). + + In moonlight proxy generator (svcutil -moonlight) mode, sync + methods will be removed at svcutil itself. + This fix brings sync proxy methods back to monotouch. + +2010-01-19 Atsushi Enomoto + + * ServiceAuthorizationBehavior.cs : implement (it does almost + nothing though). + +2010-01-13 Atsushi Enomoto + + * ContractDescriptionGenerator.cs : fill Operation.Faults. + +2010-01-08 Atsushi Enomoto + + * ContractDescriptionGenerator.cs : fix GetCallbackContract() to + correctly retrieve ServiceContractAttribute from the service type, + not the callback type. This ended up to get the bug #567672 sample + working (but it will break at some stage as it involves some + non-implemented classes). + 2009-12-18 Atsushi Enomoto * ServiceContractGenerator.cs : diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ClientCredentials.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ClientCredentials.cs index 7aaf39028ce70..fad6fbdd2600d 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ClientCredentials.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ClientCredentials.cs @@ -133,17 +133,19 @@ public override SecurityTokenManager CreateSecurityTokenManager () throw new NotImplementedException (); } - void IEndpointBehavior.AddBindingParameters (ServiceEndpoint endpoint, - BindingParameterCollection parameters) - { - parameters.Add (this); - } - void IEndpointBehavior.ApplyDispatchBehavior (ServiceEndpoint endpoint, EndpointDispatcher dispatcher) { // documented as to have no effect. } +#endif + +#if !NET_2_1 || MONOTOUCH + void IEndpointBehavior.AddBindingParameters (ServiceEndpoint endpoint, + BindingParameterCollection parameters) + { + parameters.Add (this); + } [MonoTODO] public virtual void ApplyClientBehavior ( diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescription.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescription.cs index 3d5660dd33e0e..b7fd634fe5464 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescription.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescription.cs @@ -153,7 +153,7 @@ internal ClientRuntime CreateClientRuntime () foreach (OperationDescription od in Operations) { if (!proxy.Operations.Contains (od.Name)) PopulateClientOperation (proxy, od); -#if !NET_2_1 +#if !NET_2_1 || MONOTOUCH foreach (IOperationBehavior ob in od.Behaviors) ob.ApplyClientBehavior (od, proxy.Operations [od.Name]); #endif diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescriptionGenerator.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescriptionGenerator.cs index edba80ea36273..1a72a53564881 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescriptionGenerator.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ContractDescriptionGenerator.cs @@ -29,6 +29,7 @@ using System.Collections; using System.Collections.Generic; using System.Collections.ObjectModel; +using System.Linq; using System.Net.Security; using System.Reflection; using System.Runtime.Serialization; @@ -91,28 +92,28 @@ public static MessageContractAttribute GetMessageContractAttribute (Type type) return null; } - public static ContractDescription GetCallbackContract (Type type) + public static ContractDescription GetCallbackContract (Type serviceType, Type callbackType) { - return GetContract (type, null, true); + return GetContract (callbackType, null, serviceType); } public static ContractDescription GetContract ( Type givenContractType, Type givenServiceType) { - return GetContract (givenContractType, givenServiceType, false); + return GetContract (givenContractType, givenServiceType, null); } - static ContractDescription GetContract (Type givenContractType, Type givenServiceType, bool assumeServiceContract) + static ContractDescription GetContract (Type givenContractType, Type givenServiceType, Type serviceTypeForCallback) { // FIXME: serviceType should be used for specifying attributes like OperationBehavior. Type exactContractType = null; ServiceContractAttribute sca = null; Dictionary contracts = - GetServiceContractAttributes (givenServiceType ?? givenContractType); + GetServiceContractAttributes (serviceTypeForCallback ?? givenServiceType ?? givenContractType); if (contracts.ContainsKey(givenContractType)) { exactContractType = givenContractType; - sca = contracts[givenContractType]; + sca = contracts [givenContractType]; } else { foreach (Type t in contracts.Keys) if (t.IsAssignableFrom(givenContractType)) { @@ -127,10 +128,10 @@ static ContractDescription GetContract (Type givenContractType, Type givenServic if (exactContractType == null) exactContractType = givenContractType; if (sca == null) { - if (assumeServiceContract) - sca = new ServiceContractAttribute (); + if (serviceTypeForCallback != null) + sca = contracts.Values.First (); else - throw new InvalidOperationException (String.Format ("Attempted to get contract type from '{0}' which neither is a service contract nor does it inherit service contract.", givenContractType)); + throw new InvalidOperationException (String.Format ("Attempted to get contract type from '{0}' which neither is a service contract nor does it inherit service contract.", serviceTypeForCallback ?? givenContractType)); } string name = sca.Name ?? exactContractType.Name; string ns = sca.Namespace ?? "http://tempuri.org/"; @@ -244,6 +245,8 @@ static IEnumerable GetAllInterfaceTypes (Type type) foreach (ServiceKnownTypeAttribute a in serviceMethod.GetCustomAttributes (typeof (ServiceKnownTypeAttribute), false)) foreach (Type t in a.GetTypes ()) od.KnownTypes.Add (t); + foreach (FaultContractAttribute a in serviceMethod.GetCustomAttributes (typeof (FaultContractAttribute), false)) + od.Faults.Add (new FaultDescription (a.Action) { DetailType = a.DetailType, Name = a.Name, Namespace = a.Namespace }); cd.Operations.Add (od); } else if (oca.AsyncPattern && od.BeginMethod != null || diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/IEndpointBehavior.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/IEndpointBehavior.cs index 6eb47ec704580..1ba9d63f7e5c8 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/IEndpointBehavior.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/IEndpointBehavior.cs @@ -33,12 +33,16 @@ namespace System.ServiceModel.Description { public interface IEndpointBehavior { +#if !NET_2_1 || MONOTOUCH void AddBindingParameters (ServiceEndpoint endpoint, BindingParameterCollection parameters); +#if !NET_2_1 void ApplyDispatchBehavior (ServiceEndpoint serviceEndpoint, EndpointDispatcher dispatcher); +#endif void ApplyClientBehavior (ServiceEndpoint serviceEndpoint, ClientRuntime behavior); void Validate (ServiceEndpoint serviceEndpoint); +#endif } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/IOperationBehavior.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/IOperationBehavior.cs index aa67812dfe50b..1dfda7de65cac 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/IOperationBehavior.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/IOperationBehavior.cs @@ -37,9 +37,11 @@ public interface IOperationBehavior OperationDescription description, BindingParameterCollection parameters); +#if !NET_2_1 void ApplyDispatchBehavior ( OperationDescription description, DispatchOperation dispatch); +#endif void ApplyClientBehavior ( OperationDescription description, diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceAuthorizationBehavior.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceAuthorizationBehavior.cs index 6108a34fba6b5..216c2a2526cbf 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceAuthorizationBehavior.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceAuthorizationBehavior.cs @@ -85,13 +85,22 @@ public ServiceAuthorizationBehavior () ServiceDescription description, ServiceHostBase serviceHostBase) { + foreach (ChannelDispatcher cd in serviceHostBase.ChannelDispatchers) + foreach (var ed in cd.Endpoints) { + var dr = ed.DispatchRuntime; + dr.ExternalAuthorizationPolicies = ExternalAuthorizationPolicies; + dr.ImpersonateCallerForAllOperations = ImpersonateCallerForAllOperations; + dr.PrincipalPermissionMode = PrincipalPermissionMode; + dr.RoleProvider = RoleProvider; + dr.ServiceAuthorizationManager = ServiceAuthorizationManager; + } } [MonoTODO] void IServiceBehavior.Validate ( ServiceDescription description, ServiceHostBase serviceHostBase) - { + { } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceContractGenerator.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceContractGenerator.cs index f63703a346bf8..459813ebfd3c2 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceContractGenerator.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Description/ServiceContractGenerator.cs @@ -320,53 +320,15 @@ void AddOperationMethods (CodeTypeDeclaration type, ContractDescription cd) foreach (OperationDescription od in cd.Operations) { CodeMemberMethod syncMethod = null, beginMethod = null, endMethod = null; - CodeMemberMethod cm = new CodeMemberMethod (); - type.Members.Add (cm); - if (GenerateAsync) { - cm.Name = "Begin" + od.Name; - beginMethod = cm; - } else { - cm.Name = od.Name; - syncMethod = cm; - } CodeTypeReference returnTypeFromMessageContract = null; + syncMethod = GenerateOperationMethod (type, cd, od, false, out returnTypeFromMessageContract); + type.Members.Add (syncMethod); - if (od.SyncMethod != null) { - ExportParameters (cm, od.SyncMethod.GetParameters ()); - if (GenerateAsync) { - AddBeginAsyncArgs (cm); - cm.ReturnType = new CodeTypeReference (typeof (IAsyncResult)); - } - else - cm.ReturnType = new CodeTypeReference (od.SyncMethod.ReturnType); - } else { - ExportMessages (od.Messages, cm, false); - returnTypeFromMessageContract = cm.ReturnType; - if (GenerateAsync) { - AddBeginAsyncArgs (cm); - cm.ReturnType = new CodeTypeReference (typeof (IAsyncResult)); - } - } - - // [OperationContract (Action = "...", ReplyAction = "..")] - CodeAttributeDeclaration ad = - new CodeAttributeDeclaration ( - new CodeTypeReference ( - typeof (OperationContractAttribute))); - foreach (MessageDescription md in od.Messages) { - if (md.Direction == MessageDirection.Input) - ad.Arguments.Add (new CodeAttributeArgument ("Action", new CodePrimitiveExpression (md.Action))); - else - ad.Arguments.Add (new CodeAttributeArgument ("ReplyAction", new CodePrimitiveExpression (md.Action))); - } - if (GenerateAsync) - ad.Arguments.Add (new CodeAttributeArgument ("AsyncPattern", new CodePrimitiveExpression (true))); - cm.CustomAttributes.Add (ad); - - // For async mode, add EndXxx() too. if (GenerateAsync) { + beginMethod = GenerateOperationMethod (type, cd, od, true, out returnTypeFromMessageContract); + type.Members.Add (beginMethod); - cm = new CodeMemberMethod (); + var cm = new CodeMemberMethod (); type.Members.Add (cm); cm.Name = "End" + od.Name; endMethod = cm; @@ -388,6 +350,48 @@ void AddOperationMethods (CodeTypeDeclaration type, ContractDescription cd) } } + CodeMemberMethod GenerateOperationMethod (CodeTypeDeclaration type, ContractDescription cd, OperationDescription od, bool async, out CodeTypeReference returnType) + { + CodeMemberMethod cm = new CodeMemberMethod (); + + if (async) + cm.Name = "Begin" + od.Name; + else + cm.Name = od.Name; + + if (od.SyncMethod != null) { + ExportParameters (cm, od.SyncMethod.GetParameters ()); + if (async) { + AddBeginAsyncArgs (cm); + cm.ReturnType = new CodeTypeReference (typeof (IAsyncResult)); + } + else + cm.ReturnType = new CodeTypeReference (od.SyncMethod.ReturnType); + returnType = new CodeTypeReference (od.SyncMethod.ReturnType); + } else { + ExportMessages (od.Messages, cm, false); + returnType = cm.ReturnType; + if (async) { + AddBeginAsyncArgs (cm); + cm.ReturnType = new CodeTypeReference (typeof (IAsyncResult)); + } + } + + // [OperationContract (Action = "...", ReplyAction = "..")] + var ad = new CodeAttributeDeclaration (new CodeTypeReference (typeof (OperationContractAttribute))); + foreach (MessageDescription md in od.Messages) { + if (md.Direction == MessageDirection.Input) + ad.Arguments.Add (new CodeAttributeArgument ("Action", new CodePrimitiveExpression (md.Action))); + else + ad.Arguments.Add (new CodeAttributeArgument ("ReplyAction", new CodePrimitiveExpression (md.Action))); + } + if (async) + ad.Arguments.Add (new CodeAttributeArgument ("AsyncPattern", new CodePrimitiveExpression (true))); + cm.CustomAttributes.Add (ad); + + return cm; + } + void ExportParameters (CodeMemberMethod method, ParameterInfo [] parameters) { foreach (ParameterInfo pi in parameters) @@ -400,53 +404,17 @@ void ExportParameters (CodeMemberMethod method, ParameterInfo [] parameters) void AddImplementationClientMethods (CodeTypeDeclaration type, ContractDescription cd) { foreach (OperationDescription od in cd.Operations) { - CodeMemberMethod cm = new CodeMemberMethod (); - type.Members.Add (cm); - if (GenerateAsync) - cm.Name = "Begin" + od.Name; - else - cm.Name = od.Name; - cm.Attributes = MemberAttributes.Public - | MemberAttributes.Final; + CodeMemberMethod cm; CodeTypeReference returnTypeFromMessageContract = null; + cm = GenerateImplementationClientMethod (type, cd, od, false, out returnTypeFromMessageContract); + type.Members.Add (cm); - List args = new List (); - if (od.SyncMethod != null) { - ParameterInfo [] pars = od.SyncMethod.GetParameters (); - ExportParameters (cm, pars); - cm.ReturnType = new CodeTypeReference (od.SyncMethod.ReturnType); - int i = 0; - foreach (ParameterInfo pi in pars) - args.Add (new CodeArgumentReferenceExpression (pi.Name)); - } else { - args.AddRange (ExportMessages (od.Messages, cm, true)); - returnTypeFromMessageContract = cm.ReturnType; - if (GenerateAsync) { - AddBeginAsyncArgs (cm); - cm.ReturnType = new CodeTypeReference (typeof (IAsyncResult)); - } - } - if (GenerateAsync) { - args.Add (new CodeArgumentReferenceExpression ("asyncCallback")); - args.Add (new CodeArgumentReferenceExpression ("userState")); - } - - CodeExpression call = new CodeMethodInvokeExpression ( - new CodePropertyReferenceExpression ( - new CodeBaseReferenceExpression (), - "Channel"), - cm.Name, - args.ToArray ()); - - if (cm.ReturnType.BaseType == "System.Void") - cm.Statements.Add (new CodeExpressionStatement (call)); - else - cm.Statements.Add (new CodeMethodReturnStatement (call)); - - // For async mode, add EndXxx() too. if (!GenerateAsync) continue; + cm = GenerateImplementationClientMethod (type, cd, od, true, out returnTypeFromMessageContract); + type.Members.Add (cm); + // EndXxx() implementation cm = new CodeMemberMethod (); @@ -467,7 +435,7 @@ void AddImplementationClientMethods (CodeTypeDeclaration type, ContractDescripti if (od.EndMethod != null) resultArgName = od.EndMethod.GetParameters () [0].Name; - call = new CodeMethodInvokeExpression ( + var call = new CodeMethodInvokeExpression ( new CodePropertyReferenceExpression ( new CodeBaseReferenceExpression (), "Channel"), @@ -481,6 +449,51 @@ void AddImplementationClientMethods (CodeTypeDeclaration type, ContractDescripti } } + CodeMemberMethod GenerateImplementationClientMethod (CodeTypeDeclaration type, ContractDescription cd, OperationDescription od, bool async, out CodeTypeReference returnTypeFromMessageContract) + { + CodeMemberMethod cm = new CodeMemberMethod (); + if (async) + cm.Name = "Begin" + od.Name; + else + cm.Name = od.Name; + cm.Attributes = MemberAttributes.Public | MemberAttributes.Final; + returnTypeFromMessageContract = null; + + List args = new List (); + if (od.SyncMethod != null) { + ParameterInfo [] pars = od.SyncMethod.GetParameters (); + ExportParameters (cm, pars); + cm.ReturnType = new CodeTypeReference (od.SyncMethod.ReturnType); + int i = 0; + foreach (ParameterInfo pi in pars) + args.Add (new CodeArgumentReferenceExpression (pi.Name)); + } else { + args.AddRange (ExportMessages (od.Messages, cm, true)); + returnTypeFromMessageContract = cm.ReturnType; + if (async) { + AddBeginAsyncArgs (cm); + cm.ReturnType = new CodeTypeReference (typeof (IAsyncResult)); + } + } + if (async) { + args.Add (new CodeArgumentReferenceExpression ("asyncCallback")); + args.Add (new CodeArgumentReferenceExpression ("userState")); + } + + CodeExpression call = new CodeMethodInvokeExpression ( + new CodePropertyReferenceExpression ( + new CodeBaseReferenceExpression (), + "Channel"), + cm.Name, + args.ToArray ()); + + if (cm.ReturnType.BaseType == "System.Void") + cm.Statements.Add (new CodeExpressionStatement (call)); + else + cm.Statements.Add (new CodeMethodReturnStatement (call)); + return cm; + } + CodeMemberMethod FindByName (CodeTypeDeclaration type, string name) { foreach (var m in type.Members) { diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChangeLog b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChangeLog index 568c7bf9fc4bf..b5fd81222afe7 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChangeLog +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChangeLog @@ -1,3 +1,36 @@ +2010-02-04 Atsushi Enomoto + + * ChannelDispatcher.cs : now I can enable service throttling to + handle more than one concurrent channels as ASP.NET reply channel + got fixed. + +2010-01-25 Atsushi Enomoto + + * ChannelDispatcher.cs : actually instance context provider could be + null through the entire service run. + + Fixed all current nunit failures! + +2010-01-22 Atsushi Enomoto + + * ChannelDispatcher.cs : do not try to iterate channel acceptor when + it is being closed. + +2010-01-19 Atsushi Enomoto + + * ChannelDispatcher.cs : another error audit. + +2010-01-13 Atsushi Enomoto + + * FaultContractInfo.cs : implement. + * DispatchOperation.cs, ClientOperation.cs: fill Faults. + +2010-01-08 Atsushi Enomoto + + * EndpointDispatcher.cs, InputOrReplyRequestProcessor.cs : + Pass service type to correctly retrieve ServiceContractAttribute + from the service type, not callback type. + 2010-01-07 Atsushi Enomoto * ChannelDispatcher.cs : make sure to unlock channel acceptor wait diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChannelDispatcher.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChannelDispatcher.cs index 3d467dcccd20b..ea3bd35f6863a 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChannelDispatcher.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ChannelDispatcher.cs @@ -358,10 +358,6 @@ public void Setup (TimeSpan openTimeout) public void Start () { - foreach (var ed in owner.Endpoints) - if (ed.DispatchRuntime.InstanceContextProvider == null) - ed.DispatchRuntime.InstanceContextProvider = new DefaultInstanceContextProvider (); - if (loop_thread == null) loop_thread = new Thread (new ThreadStart (Loop)); loop_thread.Start (); @@ -421,8 +417,11 @@ public void Stop (TimeSpan timeout) stop_handle.Close (); stop_handle = null; } - if (owner.Listener.State != CommunicationState.Closed) + if (owner.Listener.State != CommunicationState.Closed) { + // FIXME: log it + Console.WriteLine ("Channel listener '{0}' is not closed. Aborting.", owner.Listener.GetType ()); owner.Listener.Abort (); + } if (loop_thread != null && loop_thread.IsAlive) loop_thread.Abort (); loop_thread = null; @@ -467,9 +466,8 @@ void LoopCore () // http://social.msdn.microsoft.com/Forums/en-US/wcf/thread/3faa4a5e-8602-4dbe-a181-73b3f581835e while (loop) { - // FIXME: enable throttling and allow more than one connection to process at a time. - while (loop && channels.Count < 1) { -// while (loop && channels.Count < owner.ServiceThrottle.MaxConcurrentSessions) { + // FIXME: also consider MaxConcurrentCalls + while (loop && channels.Count < owner.ServiceThrottle.MaxConcurrentSessions) { channel_acceptor (); creator_handle.WaitOne (); // released by ChannelAccepted() } @@ -591,7 +589,7 @@ void ProcessRequest (IReplyChannel reply, RequestContext rc) if (rc != null) rc.Close (); // unless it is closed by session/call manager, move it back to the loop to receive the next message. - if (reply.State != CommunicationState.Closed) + if (loop && reply.State != CommunicationState.Closed) ProcessRequestOrInput (reply); } } @@ -609,7 +607,7 @@ void ProcessInput (IInputChannel input, Message message) Console.WriteLine (ex); } finally { // unless it is closed by session/call manager, move it back to the loop to receive the next message. - if (input.State != CommunicationState.Closed) + if (loop && input.State != CommunicationState.Closed) ProcessRequestOrInput (input); } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ClientOperation.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ClientOperation.cs index 42ce0bcc6d1e1..d7b99c9513deb 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ClientOperation.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/ClientOperation.cs @@ -60,6 +60,9 @@ protected override string GetKeyForItem (ClientOperation o) IClientMessageFormatter formatter, actual_formatter; SynchronizedCollection inspectors = new SynchronizedCollection (); +#if !NET_2_1 + SynchronizedCollection fault_contract_infos; +#endif public ClientOperation (ClientRuntime parent, string name, string action) @@ -103,7 +106,15 @@ SynchronizedCollection inspectors #if !NET_2_1 public SynchronizedCollection FaultContractInfos { - get { throw new NotImplementedException (); } + get { + if (fault_contract_infos == null) { + var l = new SynchronizedCollection (); + foreach (var f in Description.Faults) + l.Add (new FaultContractInfo (f.Action, f.DetailType)); + fault_contract_infos = l; + } + return fault_contract_infos; + } } #endif diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/DispatchOperation.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/DispatchOperation.cs index 7597b90ba86e8..c550e9cf3e8b7 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/DispatchOperation.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/DispatchOperation.cs @@ -59,8 +59,7 @@ protected override string GetKeyForItem (DispatchOperation o) IOperationInvoker invoker; SynchronizedCollection inspectors = new SynchronizedCollection (); - SynchronizedCollection fault_contract_infos - = new SynchronizedCollection (); + SynchronizedCollection fault_contract_infos; SynchronizedCollection ctx_initializers = new SynchronizedCollection (); @@ -107,7 +106,15 @@ SynchronizedCollection ctx_initializers } public SynchronizedCollection FaultContractInfos { - get { return fault_contract_infos; } + get { + if (fault_contract_infos == null) { + var l = new SynchronizedCollection (); + foreach (var f in Description.Faults) + l.Add (new FaultContractInfo (f.Action, f.DetailType)); + fault_contract_infos = l; + } + return fault_contract_infos; + } } public IDispatchMessageFormatter Formatter { diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/EndpointDispatcher.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/EndpointDispatcher.cs index 8770fa2360c80..5c29cb4eaba65 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/EndpointDispatcher.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/EndpointDispatcher.cs @@ -123,7 +123,7 @@ internal void InitializeServiceEndpoint (bool isCallback, Type serviceType, Serv //Build the dispatch operations DispatchRuntime db = this.DispatchRuntime; if (!isCallback && se.Contract.CallbackContractType != null) { - var ccd = ContractDescriptionGenerator.GetCallbackContract (se.Contract.CallbackContractType); + var ccd = ContractDescriptionGenerator.GetCallbackContract (db.Type, se.Contract.CallbackContractType); db.CallbackClientRuntime = ccd.CreateClientRuntime (); db.CallbackClientRuntime.CallbackClientType = ccd.ContractType; } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/FaultContractInfo.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/FaultContractInfo.cs index 4c58b78227a1f..98f44a5aef174 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/FaultContractInfo.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/FaultContractInfo.cs @@ -31,19 +31,18 @@ namespace System.ServiceModel.Dispatcher { public class FaultContractInfo { - string action; - Type detail; - public FaultContractInfo (string action, Type detail) { + if (action == null) + throw new ArgumentNullException ("action"); + if (detail == null) + throw new ArgumentNullException ("detail"); + Action = action; + Detail = detail; } - public string Action { - get { return action; } - } + public string Action { get; private set; } - public Type Detail { - get { return detail; } - } + public Type Detail { get; private set; } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/InputOrReplyRequestProcessor.cs b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/InputOrReplyRequestProcessor.cs index e2615c6ae41af..74a4daa0e35ff 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/InputOrReplyRequestProcessor.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Dispatcher/InputOrReplyRequestProcessor.cs @@ -55,7 +55,7 @@ OperationContext CreateOperationContext (Message incoming) { ServiceRuntimeChannel contextChannel; if (dispatch_runtime.HasCallbackRuntime) { - var type = ServiceProxyGenerator.CreateCallbackProxyType (dispatch_runtime.CallbackClientRuntime.CallbackClientType); + var type = ServiceProxyGenerator.CreateCallbackProxyType (dispatch_runtime.Type, dispatch_runtime.CallbackClientRuntime.CallbackClientType); contextChannel = (ServiceRuntimeChannel) Activator.CreateInstance (type, new object [] {reply_or_input, dispatch_runtime}); } else diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.Security/ChangeLog b/mcs/class/System.ServiceModel/System.ServiceModel.Security/ChangeLog index 274be2ee1c3f1..8a5bda7e937b3 100755 --- a/mcs/class/System.ServiceModel/System.ServiceModel.Security/ChangeLog +++ b/mcs/class/System.ServiceModel/System.ServiceModel.Security/ChangeLog @@ -1,3 +1,8 @@ +2010-01-18 Atsushi Enomoto + + * SecureConversationVersion.cs, SecurityPolicyVersion.cs, + TrustVersion.cs : add new 3.5 classes. + 2007-04-17 Atsushi Enomoto * WSSecurityTokenSerializer.cs : write GenericXmlSecurityToken (btw diff --git a/mcs/class/System.ServiceModel/System.ServiceModel.dll.sources b/mcs/class/System.ServiceModel/System.ServiceModel.dll.sources index db43f33625f86..9b1839b4a7b15 100755 --- a/mcs/class/System.ServiceModel/System.ServiceModel.dll.sources +++ b/mcs/class/System.ServiceModel/System.ServiceModel.dll.sources @@ -763,12 +763,14 @@ System.ServiceModel.Security/MessageSecurityException.cs System.ServiceModel.Security/PeerCredential.cs System.ServiceModel.Security/ScopedMessagePartSpecification.cs System.ServiceModel.Security/SecureConversationServiceCredential.cs +System.ServiceModel.Security/SecureConversationVersion.cs System.ServiceModel.Security/SecurityAccessDeniedException.cs System.ServiceModel.Security/SecurityAlgorithmSuite.cs System.ServiceModel.Security/SecurityContextKeyIdentifierClause.cs System.ServiceModel.Security/SecurityCredentialsManager.cs System.ServiceModel.Security/SecurityMessageProperty.cs System.ServiceModel.Security/SecurityNegotiationException.cs +System.ServiceModel.Security/SecurityPolicyVersion.cs System.ServiceModel.Security/SecurityStateEncoder.cs System.ServiceModel.Security/SecurityTokenAttachmentMode.cs System.ServiceModel.Security/SecurityTokenSpecification.cs @@ -776,6 +778,7 @@ System.ServiceModel.Security/SecurityVersion.cs System.ServiceModel.Security/ServiceCredentialsSecurityTokenManager.cs System.ServiceModel.Security/SspiSecurityTokenProvider.cs System.ServiceModel.Security/SupportingTokenSpecification.cs +System.ServiceModel.Security/TrustVersion.cs System.ServiceModel.Security/UnionSecurityTokenResolver.cs System.ServiceModel.Security/UserNamePasswordClientCredential.cs System.ServiceModel.Security/UserNamePasswordServiceCredential.cs @@ -900,6 +903,7 @@ System.ServiceModel/ServiceHostingEnvironment.cs System.ServiceModel/ServiceKnownTypeAttribute.cs System.ServiceModel/ServiceRuntimeChannel.cs System.ServiceModel/ServiceSecurityContext.cs +System.ServiceModel/SilverlightClientConfigLoader.cs System.ServiceModel/SpnEndpointIdentity.cs System.ServiceModel/TcpTransportSecurity.cs System.ServiceModel/TransactionFlowAttribute.cs diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/BasicHttpBinding.cs b/mcs/class/System.ServiceModel/System.ServiceModel/BasicHttpBinding.cs index e805b0fc0a63f..336656d30a016 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/BasicHttpBinding.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/BasicHttpBinding.cs @@ -91,6 +91,10 @@ public BasicHttpBinding (string configurationName) set { bypass_proxy_on_local = value; } } +#if NET_2_1 + public bool EnableHttpCookieContainer { get; set; } +#endif + public HostNameComparisonMode HostNameComparisonMode { get { return host_name_comparison_mode; } set { host_name_comparison_mode = value; } @@ -176,6 +180,7 @@ public BasicHttpBinding (string configurationName) public override BindingElementCollection CreateBindingElements () { + var list = new List (); switch (Security.Mode) { #if !NET_2_1 case BasicHttpSecurityMode.Message: @@ -189,14 +194,20 @@ public override BindingElementCollection sec = SecurityBindingElement.CreateCertificateOverTransportBindingElement (); else sec = new AsymmetricSecurityBindingElement (); - return new BindingElementCollection (new BindingElement [] {sec, BuildMessageEncodingBindingElement (), GetTransport ()}); + list.Add (sec); + break; #endif - default: - return new BindingElementCollection (new BindingElement [] { - BuildMessageEncodingBindingElement (), - GetTransport ()}); } +#if NET_2_1 + if (EnableHttpCookieContainer) + list.Add (new HttpCookieContainerBindingElement ()); +#endif + + list.Add (BuildMessageEncodingBindingElement ()); + list.Add (GetTransport ()); + + return new BindingElementCollection (list.ToArray ()); } MessageEncodingBindingElement BuildMessageEncodingBindingElement () diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ChangeLog b/mcs/class/System.ServiceModel/System.ServiceModel/ChangeLog index 814a061a3b235..b2ffc69fc8ea7 100755 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ChangeLog +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ChangeLog @@ -1,3 +1,71 @@ +2010-01-25 Atsushi Enomoto + + * ChannelFactory_1.cs, ChannelFactory.cs : fix default constructor + handling and ensure service endpoint at opening the factory. + +2010-01-22 Atsushi Enomoto + + * ServiceHostBase.cs : fix complicated IMetadataExchange handling to + pass nunit tests (treat mex binding as special case). + +2010-01-22 Atsushi Enomoto + + * DuplexClientRuntimeChannel.cs : do not try to iterate channel + acceptor when it is being closed. + +2010-01-20 Atsushi Enomoto + + * ServiceHostBase.cs : a stability workaround to make nunit test + stopper almost reproducible. + +2010-01-19 Atsushi Enomoto + + * WS2007FederationHttpBinding.cs, WS2007HttpBinding.cs: + add missing constructors. + +2010-01-18 Atsushi Enomoto + + * MessageSecurityVersion.cs : add new 3.5 members. + +2010-01-15 Atsushi Enomoto + + * SilverlightClientConfigLoader.cs : add another loop blocker. + Do not reject binding configuration with no basic http binding. + In SL3 it may be custom and such configuration should be valid. + +2010-01-13 Atsushi Enomoto + + * ExceptionDetail.cs : uncomment DataMember (likely commented out due + to missing default serialization in the past). + +2010-01-13 Atsushi Enomoto + + * EndpointAddressBuilder.cs : reader getters were broken. + +2010-01-13 Atsushi Enomoto + + * EndpointAddressBuilder.cs : implement. + +2010-01-13 Atsushi Enomoto + + * BasicHttpBinding.cs : add SL3 EnableHttpCookieContainer support. + +2010-01-10 Atsushi Enomoto + + * SilverlightClientConfigLoader.cs : uncomment binary message + encoding element which was internal-only in SL2 but public in SL3. + +2010-01-08 Atsushi Enomoto + + * ServiceProxyGenerator.cs, ServiceRuntimeChannel.cs : + Pass service type to correctly retrieve ServiceContractAttribute + from the service type, not callback type. + +2010-01-08 Atsushi Enomoto + + * ClientRuntimeChannel.cs : to open duplex callback channel, it must + ensure to open the channel itself (not only its inner channel). + 2009-12-18 Atsushi Enomoto * ClientBase.cs : remove extra CWLs. diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory.cs index c59abe443208c..15e5eb3e7978b 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory.cs @@ -251,6 +251,15 @@ void IDisposable.Dispose () protected void EnsureOpened () { + if (Endpoint == null) + throw new InvalidOperationException ("A service endpoint must be configured for this channel factory"); + if (Endpoint.Address == null) + throw new InvalidOperationException ("An EndpointAddress must be configured for this channel factory"); + if (Endpoint.Contract == null) + throw new InvalidOperationException ("A service Contract must be configured for this channel factory"); + if (Endpoint.Binding == null) + throw new InvalidOperationException ("A Binding must be configured for this channel factory"); + if (State != CommunicationState.Opened) Open (); } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory_1.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory_1.cs index 4eab5c3347b39..d9314d3e1d9ea 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory_1.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ChannelFactory_1.cs @@ -40,7 +40,6 @@ public class ChannelFactory : ChannelFactory, IChannelFactory { public ChannelFactory () - : this ("*") { } @@ -103,6 +102,8 @@ public ChannelFactory (Binding binding, EndpointAddress remoteAddress) public TChannel CreateChannel () { + EnsureOpened (); + return CreateChannel (Endpoint.Address); } @@ -133,6 +134,10 @@ public virtual TChannel CreateChannel (EndpointAddress address, Uri via) #if MONOTOUCH throw new InvalidOperationException ("MonoTouch does not support dynamic proxy code generation. Override this method or its caller to return specific client proxy instance"); #else + var existing = Endpoint.Address; + try { + + Endpoint.Address = address; EnsureOpened (); Endpoint.Validate (); Type type = ClientProxyGenerator.CreateProxyType (typeof (TChannel), Endpoint.Contract, false); @@ -142,6 +147,10 @@ public virtual TChannel CreateChannel (EndpointAddress address, Uri via) // that should work either. object proxy = Activator.CreateInstance (type, new object [] {Endpoint, this, address ?? Endpoint.Address, via}); return (TChannel) proxy; + + } finally { + Endpoint.Address = existing; + } #endif } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ClientRuntimeChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ClientRuntimeChannel.cs index 083c6d780b565..7102ca116ca6b 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ClientRuntimeChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ClientRuntimeChannel.cs @@ -435,6 +435,10 @@ object DoProcess (MethodBase method, string operationName, object [] parameters) if (AllowInitializationUI) DisplayInitializationUI (); OperationDescription od = SelectOperation (method, operationName, parameters); + + if (State != CommunicationState.Opened) + Open (); + if (!od.IsOneWay) return Request (od, parameters); else { @@ -458,18 +462,12 @@ OperationDescription SelectOperation (MethodBase method, string operationName, o void Output (OperationDescription od, object [] parameters) { - if (OutputChannel.State != CommunicationState.Opened) - OutputChannel.Open (); - ClientOperation op = runtime.Operations [od.Name]; Send (CreateRequest (op, parameters), OperationTimeout); } object Request (OperationDescription od, object [] parameters) { - if (OperationChannel.State != CommunicationState.Opened) - OperationChannel.Open (); - ClientOperation op = runtime.Operations [od.Name]; object [] inspections = new object [runtime.MessageInspectors.Count]; Message req = CreateRequest (op, parameters); diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/DuplexClientRuntimeChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel/DuplexClientRuntimeChannel.cs index ef8f80047254d..43d6e2168ec78 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/DuplexClientRuntimeChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/DuplexClientRuntimeChannel.cs @@ -164,7 +164,7 @@ void ProcessInput (IInputChannel input, Message message) Console.WriteLine (ex); } finally { // unless it is closed by session/call manager, move it back to the loop to receive the next message. - if (input.State != CommunicationState.Closed) + if (loop && input.State != CommunicationState.Closed) ProcessRequestOrInput (input); } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/EndpointAddressBuilder.cs b/mcs/class/System.ServiceModel/System.ServiceModel/EndpointAddressBuilder.cs index a801c579ec2f9..27e5d72869be3 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/EndpointAddressBuilder.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/EndpointAddressBuilder.cs @@ -27,6 +27,8 @@ // using System; using System.Collections.ObjectModel; +using System.IO; +using System.Linq; using System.Xml; using System.ServiceModel.Channels; @@ -37,7 +39,7 @@ public class EndpointAddressBuilder Collection headers = new Collection (); EndpointIdentity identity; Uri uri; - XmlDictionaryReader ext, meta; + string extension, metadata; public EndpointAddressBuilder () { @@ -55,44 +57,65 @@ public EndpointAddressBuilder (EndpointAddress address) get { return headers; } } - [MonoTODO] - public EndpointIdentity Identity { - get { return identity; } - set { identity = value; } - } - - [MonoTODO] public Uri Uri { get { return uri; } set { uri = value; } } - [MonoTODO] +#if !NET_2_1 + public EndpointIdentity Identity { + get { return identity; } + set { identity = value; } + } + public XmlDictionaryReader GetReaderAtExtensions () { - throw new NotImplementedException (); + if (extension == null) + return null; + var r = XmlDictionaryReader.CreateDictionaryReader (XmlReader.Create (new StringReader (extension))); + r.MoveToContent (); + return r; } - [MonoTODO] public XmlDictionaryReader GetReaderAtMetadata () { - throw new NotImplementedException (); + if (metadata == null) + return null; + var r = XmlDictionaryReader.CreateDictionaryReader (XmlReader.Create (new StringReader (metadata))); + r.MoveToContent (); + return r; } public void SetExtensionReader (XmlDictionaryReader reader) { - ext = reader; + if (reader == null) + extension = null; + else { + reader.MoveToContent (); + extension = reader.ReadOuterXml (); + } } public void SetMetadataReader (XmlDictionaryReader reader) { - meta = reader; + if (reader == null) + metadata = null; + else { + reader.MoveToContent (); + metadata = reader.ReadOuterXml (); + } } public EndpointAddress ToEndpointAddress () { return new EndpointAddress (uri, identity, - new AddressHeaderCollection (headers), meta, ext); + new AddressHeaderCollection (headers), GetReaderAtMetadata (), GetReaderAtExtensions ()); + } +#else + public EndpointAddress ToEndpointAddress () + { + return new EndpointAddress (uri, headers.ToArray ()); } +#endif } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ExceptionDetail.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ExceptionDetail.cs index aeabb0be64324..2245a229b76d9 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ExceptionDetail.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ExceptionDetail.cs @@ -56,7 +56,7 @@ public ExceptionDetail (Exception exception) private set; } - //[DataMember] + [DataMember] public ExceptionDetail InnerException { get; private set; diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/MessageSecurityVersion.cs b/mcs/class/System.ServiceModel/System.ServiceModel/MessageSecurityVersion.cs index 414a07da39b61..2f53bc57b670a 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/MessageSecurityVersion.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/MessageSecurityVersion.cs @@ -98,12 +98,20 @@ public override ReadOnlyCollection GetSecuritySpecifications () class MessageSecurityVersionImpl : MessageSecurityVersion { - bool wss11, basic_profile; + bool wss11, basic_profile, use2007; - public MessageSecurityVersionImpl (bool wss11, bool basicProfile) + public MessageSecurityVersionImpl (bool wss11, bool basicProfile, bool use2007) { this.wss11 = wss11; this.basic_profile = basicProfile; + this.use2007 = use2007; + if (use2007) { + SecureConversationVersion = SecureConversationVersion.Default; + TrustVersion = TrustVersion.Default; + } else { + SecureConversationVersion = SecureConversationVersion.WSSecureConversationFeb2005; + TrustVersion = TrustVersion.WSTrustFeb2005; + } } public override BasicSecurityProfileVersion BasicSecurityProfileVersion { @@ -117,17 +125,24 @@ public MessageSecurityVersionImpl (bool wss11, bool basicProfile) public override SecurityVersion SecurityVersion { get { return wss11 ? SecurityVersion.WSSecurity11 : SecurityVersion.WSSecurity10; } } + + public override SecurityPolicyVersion SecurityPolicyVersion { + get { return use2007 ? SecurityPolicyVersion.WSSecurityPolicy12 : SecurityPolicyVersion.WSSecurityPolicy11; } + } } // Static members - static MessageSecurityVersion wss10_basic, wss11, wss11_basic; + static MessageSecurityVersion wss10_basic, wss11, wss11_basic, wss10_2007_basic, wss11_2007_basic, wss11_2007; static MessageSecurityVersion () { - wss10_basic = new MessageSecurityVersionImpl (false, true); - wss11 = new MessageSecurityVersionImpl (true, false); - wss11_basic = new MessageSecurityVersionImpl (true, true); + wss10_basic = new MessageSecurityVersionImpl (false, true, false); + wss11 = new MessageSecurityVersionImpl (true, false, false); + wss11_basic = new MessageSecurityVersionImpl (true, true, false); + wss10_2007_basic = new MessageSecurityVersionImpl (false, true, true); + wss11_2007_basic = new MessageSecurityVersionImpl (true, true, true); + wss11_2007 = new MessageSecurityVersionImpl (true, false, true); } public static MessageSecurityVersion Default { @@ -148,6 +163,18 @@ static MessageSecurityVersion () get { return wss11_basic; } } + public static MessageSecurityVersion WSSecurity10WSTrust13WSSecureConversation13WSSecurityPolicy12BasicSecurityProfile10 { + get { return wss10_2007_basic; } + } + + public static MessageSecurityVersion WSSecurity11WSTrust13WSSecureConversation13WSSecurityPolicy12BasicSecurityProfile10 { + get { return wss11_2007_basic; } + } + + public static MessageSecurityVersion WSSecurity11WSTrust13WSSecureConversation13WSSecurityPolicy12 { + get { return wss11_2007; } + } + // Instance members MessageSecurityVersion () @@ -159,5 +186,12 @@ static MessageSecurityVersion () public abstract SecurityTokenVersion SecurityTokenVersion { get; } public abstract SecurityVersion SecurityVersion { get; } + + public SecureConversationVersion SecureConversationVersion { get; internal set; } + + public abstract SecurityPolicyVersion SecurityPolicyVersion { get; } + + public TrustVersion TrustVersion { get; internal set; } + } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ServiceHostBase.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ServiceHostBase.cs index 73f8c3ad5e894..f799f9a3cd776 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ServiceHostBase.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ServiceHostBase.cs @@ -197,7 +197,7 @@ protected void AddBaseAddress (Uri baseAddress) Uri address, Uri listenUri) { EndpointAddress ea = BuildEndpointAddress (address, binding); - ContractDescription cd = GetContract (implementedContract); + ContractDescription cd = GetContract (implementedContract, binding.Name == "MetadataExchangeHttpBinding"); if (cd == null) throw new InvalidOperationException (String.Format ("Contract '{0}' was not found in the implemented contracts in this service host.", implementedContract)); return AddServiceEndpointCore (cd, binding, ea, listenUri); @@ -218,7 +218,7 @@ Type PopulateType (string typeName) ContractDescription mex_contract, help_page_contract; - ContractDescription GetContract (string name) + ContractDescription GetContract (string name, bool mexBinding) { // FIXME: not sure if they should really be special cases. switch (name) { @@ -234,30 +234,19 @@ ContractDescription GetContract (string name) // if it was added only IMetadataExchange // endpoint (and you'll see the word // "infrastructure" in the exception message). - if (Description.Behaviors.Find () == null) + if (mexBinding && Description.Behaviors.Find () == null) break; if (mex_contract == null) mex_contract = ContractDescription.GetContract (typeof (IMetadataExchange)); return mex_contract; } - // FIXME: probably type-to-contract-name mapping is wrong. - // This "loopup by type name" incorrectly allows - // "System.ServiceModel.Description.IMetadataExchange", - // but disabling this results in couple of regressions. - // So I keep enabling it so far. But it smells wrong. Type type = PopulateType (name); + if (type == null) + return null; foreach (ContractDescription cd in ImplementedContracts.Values) { - if (type == null) { - if (cd.Name == name) - return cd; - continue; - } - - // FIXME: This check is a negative side effect - // of the above hack. (but it should not still - // skip name-based match). Seealso above FIXMEs. + // This check is a negative side effect of the above match-by-name design. if (cd.ContractType == typeof (IMetadataExchange)) continue; @@ -442,10 +431,6 @@ protected void LoadConfigurationSection (ServiceElement element) ServicesSection services = ConfigUtil.ServicesSection; } - void DoOpen (TimeSpan timeout) - { - } - [MonoTODO] protected override sealed void OnAbort () { @@ -495,6 +480,9 @@ protected override sealed void OnOpen (TimeSpan timeout) InitializeRuntime (); foreach (var cd in ChannelDispatchers) cd.Open (timeout - (DateTime.Now - start)); + + // FIXME: remove this hack. It should make sure that each ChannelDispatcher's loop has started, using WaitHandle.WaitAll() or something similar. + System.Threading.Thread.Sleep (300); } protected override void OnEndClose (IAsyncResult result) diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ServiceProxyGenerator.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ServiceProxyGenerator.cs index 1efd151e42b8c..75430bef08cb6 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ServiceProxyGenerator.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ServiceProxyGenerator.cs @@ -37,9 +37,9 @@ namespace System.ServiceModel { internal class ServiceProxyGenerator : ProxyGeneratorBase { - public static Type CreateCallbackProxyType (Type type) + public static Type CreateCallbackProxyType (Type serviceType, Type callbackType) { - var cd = ContractDescriptionGenerator.GetCallbackContract (type); + var cd = ContractDescriptionGenerator.GetCallbackContract (serviceType, callbackType); string modname = "dummy"; Type crtype = typeof (DuplexServiceRuntimeChannel); @@ -47,7 +47,7 @@ public static Type CreateCallbackProxyType (Type type) CodeClass c = new CodeModule (modname).CreateClass ( "__callbackproxy_" + cd.Name, crtype, - new Type [] {type}); + new Type [] {callbackType}); // // public __callbackproxy_MyContract ( diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/ServiceRuntimeChannel.cs b/mcs/class/System.ServiceModel/System.ServiceModel/ServiceRuntimeChannel.cs index 1cf72776b879a..e07f26ed3d393 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/ServiceRuntimeChannel.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/ServiceRuntimeChannel.cs @@ -41,7 +41,7 @@ public DuplexServiceRuntimeChannel (IChannel channel, DispatchRuntime runtime) { // setup callback ClientRuntimeChannel. var crt = runtime.CallbackClientRuntime; - var cd = ContractDescriptionGenerator.GetCallbackContract (crt.CallbackClientType); + var cd = ContractDescriptionGenerator.GetCallbackContract (runtime.Type, crt.CallbackClientType); client = new ClientRuntimeChannel (crt, cd, this.DefaultOpenTimeout, this.DefaultCloseTimeout, channel, null, runtime.ChannelDispatcher.MessageVersion, this.RemoteAddress, null); } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/SilverlightClientConfigLoader.cs b/mcs/class/System.ServiceModel/System.ServiceModel/SilverlightClientConfigLoader.cs index a720556176b8c..99b33b48905ac 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/SilverlightClientConfigLoader.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/SilverlightClientConfigLoader.cs @@ -25,7 +25,7 @@ // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. // - +#if NET_2_1 using System; using System.Collections.Generic; using System.ServiceModel.Channels; @@ -145,12 +145,10 @@ CustomBindingConfiguration ReadCustomBinding (XmlReader reader) continue; } switch (reader.LocalName) { - // FIXME: binary encoder must be included in 2.1 profile. - // Since they are internal only, they have to be specially handled by linker. -// case "binaryMessageEncoding": -// b.MessageEncoding = new BinaryMessageEncodingBindingElement (); -// reader.Skip (); -// break; + case "binaryMessageEncoding": + b.MessageEncoding = new BinaryMessageEncodingBindingElement (); + reader.Skip (); + break; case "textMessageEncoding": b.MessageEncoding = new TextMessageEncodingBindingElement (); reader.Skip (); @@ -163,6 +161,8 @@ CustomBindingConfiguration ReadCustomBinding (XmlReader reader) b.Transport = new HttpsTransportBindingElement (); reader.Skip (); break; + default: + throw new XmlException (String.Format ("Unexpected configuration element '{0}'", reader.LocalName)); } } reader.ReadEndElement (); @@ -247,9 +247,6 @@ public ServiceEndpointConfiguration GetServiceEndpointConfiguration (string name EndpointConfiguration GetEndpointConfiguration (string name) { - if (Client.Endpoints.Count == 0) - throw new InvalidOperationException ("Endpoint configuration can be acquired only after loading is done."); - foreach (var e in Client.Endpoints) if (e.Name == name || name == "*") return e; @@ -258,9 +255,6 @@ EndpointConfiguration GetEndpointConfiguration (string name) BindingConfiguration GetConfiguredHttpBinding (EndpointConfiguration endpoint) { - if (Bindings.BasicHttpBinding.Count == 0) - throw new InvalidOperationException ("Binding configuration can be acquired only after loading is done."); - foreach (var b in Bindings.All ()) if (b.Name == endpoint.BindingConfiguration) return b; @@ -401,3 +395,4 @@ public EndpointConfiguration () } } } +#endif diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/WS2007FederationHttpBinding.cs b/mcs/class/System.ServiceModel/System.ServiceModel/WS2007FederationHttpBinding.cs index 5ec459d54f57c..c0b1564ff2413 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/WS2007FederationHttpBinding.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/WS2007FederationHttpBinding.cs @@ -35,5 +35,27 @@ namespace System.ServiceModel [MonoTODO] public class WS2007FederationHttpBinding : WSFederationHttpBinding { + public WS2007FederationHttpBinding () + : base () + { + } + + public WS2007FederationHttpBinding ( + WSFederationHttpSecurityMode securityMode) + : base (securityMode) + { + } + + public WS2007FederationHttpBinding (WSFederationHttpSecurityMode securityMode, bool reliableSessionEnabled) + : base (securityMode, reliableSessionEnabled) + { + } + + [MonoTODO] + public WS2007FederationHttpBinding (string configurationName) + : base (configurationName) + { + throw new NotImplementedException (); + } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel/WS2007HttpBinding.cs b/mcs/class/System.ServiceModel/System.ServiceModel/WS2007HttpBinding.cs index 08cc64629108a..4ac7a2ea4813a 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel/WS2007HttpBinding.cs +++ b/mcs/class/System.ServiceModel/System.ServiceModel/WS2007HttpBinding.cs @@ -35,5 +35,25 @@ namespace System.ServiceModel [MonoTODO] public class WS2007HttpBinding : WSHttpBinding { + public WS2007HttpBinding () + : base () + { + } + + public WS2007HttpBinding (SecurityMode mode) + : base (mode) + { + } + + public WS2007HttpBinding (SecurityMode mode, bool reliableSessionEnabled) + : base (mode, reliableSessionEnabled) + { + } + + [MonoTODO] + public WS2007HttpBinding (string configurationName) + : base (configurationName) + { + } } } diff --git a/mcs/class/System.ServiceModel/System.ServiceModel_test.dll.sources b/mcs/class/System.ServiceModel/System.ServiceModel_test.dll.sources index 635026ec5f3e7..aaeadc7b8ff67 100644 --- a/mcs/class/System.ServiceModel/System.ServiceModel_test.dll.sources +++ b/mcs/class/System.ServiceModel/System.ServiceModel_test.dll.sources @@ -161,7 +161,9 @@ FeatureBased/Features.Client/FaultsTesterProxy.cs FeatureBased/Features.Client/KnownTypeTesterProxy.cs FeatureBased/Features.Client/MessageContractTesterProxy.cs FeatureBased/Features.Client/UntypedMessageTesterProxy.cs +FeatureBased/Features.Serialization/FaultsTest.cs FeatureBased/Features.Contracts/FaultsTester.cs FeatureBased/Features.Contracts/KnownTypeTester.cs +FeatureBased/Features.Serialization/MessageContractTest.cs FeatureBased/Features.Contracts/UntypedMessageTester.cs FeatureBased/Features.Serialization/XmlComparer.cs diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/AddressHeaderTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/AddressHeaderTest.cs index fd6463c05523e..6cf655e4dcf37 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/AddressHeaderTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/AddressHeaderTest.cs @@ -51,5 +51,26 @@ public void EqualsTest () Assert.IsFalse (h.Equals (null), "#1"); // never throw nullref Assert.IsTrue (h.Equals (h2), "#2"); } + + [Test] + public void GetAddressHeaderReader () + { + var h = AddressHeader.CreateAddressHeader ("foo", String.Empty, null); + var r = h.GetAddressHeaderReader (); + r.MoveToContent (); + Assert.AreEqual ("foo", r.LocalName, "#1"); + Assert.AreEqual ("true", r.GetAttribute ("nil", XmlSchema.InstanceNamespace), "#2"); + } + + [Test] + public void WriteAddressHeader () + { + var h = AddressHeader.CreateAddressHeader ("foo", "urn:foo", null); + var sw = new StringWriter (); + var xw = XmlDictionaryWriter.CreateDictionaryWriter (XmlWriter.Create (sw)); + h.WriteAddressHeader (xw); + xw.Close (); + Assert.AreEqual ("", sw.ToString (), "#1"); + } } } diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/ChangeLog b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/ChangeLog index 9055cb41ef7db..75c583db55a9b 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/ChangeLog +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/ChangeLog @@ -1,3 +1,11 @@ +2010-01-21 Atsushi Enomoto + + * SslStreamSecurityBindingElementTest.cs : reduce extra base dep. + +2010-01-20 Atsushi Enomoto + + * AddressHeaderTest.cs : add reader and writer tests. + 2010-01-06 Atsushi Enomoto * BinaryMessageEncodingBindingElementTest.cs : added test for diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/SslStreamSecurityBindingElementTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/SslStreamSecurityBindingElementTest.cs index 01f273ecf59a3..9b63c9b83d681 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/SslStreamSecurityBindingElementTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Channels/SslStreamSecurityBindingElementTest.cs @@ -39,7 +39,7 @@ namespace MonoTests.System.ServiceModel.Channels { [TestFixture] - public class SslStreamSecurityBindingElementTest : BindingElementTest + public class SslStreamSecurityBindingElementTest { [Test] [Category ("NotWorking")] diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ChangeLog b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ChangeLog index e4b4919dc7936..4ca4eb1024926 100755 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ChangeLog +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ChangeLog @@ -1,3 +1,18 @@ +2010-01-28 Atsushi Enomoto + + * ServiceContractGeneratorTest.cs : add test for async method + generation option to generate sync methods as well. + +2010-01-22 Atsushi Enomoto + + * ServiceMetadataBehaviorTest.cs : check name constant (MSDN is + wrong here). + +2010-01-19 Atsushi Enomoto + + * ServiceAuthorizationBehaviorTest.cs : it's updated and enabled. + Added some more tests. + 2010-01-06 Atsushi Enomoto * ServiceDebugBehaviorTest.cs : make sure to close hosts. diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceAuthorizationBehaviorTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceAuthorizationBehaviorTest.cs index 719bbb2f34c57..a7cfc7807f767 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceAuthorizationBehaviorTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceAuthorizationBehaviorTest.cs @@ -25,9 +25,6 @@ // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. // -#if USE_DEPRECATED -// This class is not deprecated, but most of members and depending classes -// have changed, so most of the code is not reusable. using System; using System.Collections.ObjectModel; @@ -45,65 +42,75 @@ public class ServiceAuthorizationBehaviorTest [Test] public void DefaultValues () { - ServiceAuthorizationBehavior b = - new ServiceAuthorizationBehavior (); - Assert.IsNull (b.AuthorizationDomain, "#1"); - Assert.IsFalse (b.ImpersonateCallerForAllServiceOperations, - "#2"); - Assert.IsNull (b.OperationRequirement, "#3"); - Assert.AreEqual (PrincipalPermissionMode.UseWindowsGroups, - b.PrincipalPermissionMode, "#4"); + var b = new ServiceAuthorizationBehavior (); + Assert.IsNull (b.ExternalAuthorizationPolicies, "#1-1"); + Assert.IsFalse (b.ImpersonateCallerForAllOperations, "#1-2"); + Assert.AreEqual (PrincipalPermissionMode.UseWindowsGroups, b.PrincipalPermissionMode, "#1-3"); + + ServiceHost host = new ServiceHost (typeof (TestService)); + b = host.Description.Behaviors.Find (); + Assert.IsNull (b.ExternalAuthorizationPolicies, "#2-1"); + Assert.IsFalse (b.ImpersonateCallerForAllOperations, "#2-2"); + Assert.AreEqual (PrincipalPermissionMode.UseWindowsGroups, b.PrincipalPermissionMode, "#2-3"); } [Test] - public void ApplyBehavior () + public void Validate () { - ServiceHost host = new ServiceHost (typeof (object)); - EndpointDispatcher d = new EndpointDispatcher (host, "a", ""); - DispatchRuntime db = d.Behavior; - EndpointDispatcher d2 = new EndpointDispatcher (host, "a", ""); - DispatchRuntime db2 = d2.Behavior; + var b = new ServiceAuthorizationBehavior (); + IServiceBehavior sb = b; + sb.Validate (new ServiceDescription (), + new ServiceHost (typeof (object))); + } - ServiceAuthorizationBehavior b = - new ServiceAuthorizationBehavior (); - b.ImpersonateCallerForAllServiceOperations = true; - b.OperationRequirement = new MyRequirement (); + [Test] + [ExpectedException (typeof (InvalidOperationException))] + [Category ("NotWorking")] + public void ImpersonateCallerWithNoValidOperation () + { + ServiceHost host = new ServiceHost (typeof (TestService)); + var b = host.Description.Behaviors.Find (); + b.ImpersonateCallerForAllOperations = true; b.PrincipalPermissionMode = PrincipalPermissionMode.None; - Collection c = - new Collection ( - new DispatchRuntime [] {db, db2}); - Collection pc = - new Collection ( - new BindingParameterCollection [] { - new BindingParameterCollection ()}); - ((IServiceBehavior) b).ApplyBehavior (null, host, c, pc); + host.AddServiceEndpoint (typeof (TestService), new BasicHttpBinding (), new Uri ("http://localhost:37564")); - Assert.IsNull (db.AuthorizationDomain, "#1-1"); - Assert.IsTrue (db.ImpersonateCallerForAllServiceOperations, "#1-2"); - Assert.AreEqual (typeof (MyRequirement), - db.OperationRequirement.GetType (), "#1-3"); - Assert.AreEqual (PrincipalPermissionMode.None, - db.PrincipalPermissionMode, "#1-4"); - Assert.IsNull (db2.AuthorizationDomain, "#2-1"); - Assert.IsTrue (db2.ImpersonateCallerForAllServiceOperations, "#2-2"); - /* - Assert.AreEqual (typeof (MyRequirement), - db2.OperationRequirement.GetType (), "#2-3"); + host.Open (); + } + + [Test] + public void ApplyBehavior () + { + ServiceHost host = new ServiceHost (typeof (TestService2)); + var b = host.Description.Behaviors.Find (); + b.ImpersonateCallerForAllOperations = false; + b.PrincipalPermissionMode = PrincipalPermissionMode.None; + + host.AddServiceEndpoint (typeof (TestService2), new BasicHttpBinding (), new Uri ("http://localhost:37564")); + + host.Open (); + var ed = ((ChannelDispatcher) host.ChannelDispatchers [0]).Endpoints [0]; + var db = ed.DispatchRuntime; + host.Close (); + + Assert.IsFalse (db.ImpersonateCallerForAllOperations, "#1"); Assert.AreEqual (PrincipalPermissionMode.None, - db2.PrincipalPermissionMode, "#2-4"); - */ + db.PrincipalPermissionMode, "#2"); + } + + [ServiceContract] + public class TestService + { + [OperationContract] + public void Foo () {} } - /* - class MyRequirement : OperationRequirement + [ServiceContract] + public class TestService2 { - public override bool AccessCheck (OperationContext ctx) - { - return true; - } + [OperationContract] + [OperationBehavior (Impersonation = ImpersonationOption.Allowed)] + public void Foo () {} } - */ } } -#endif diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceMetadataBehaviorTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceMetadataBehaviorTest.cs index a33f7c3c2e796..0c96e32079a98 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceMetadataBehaviorTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel.Description/ServiceMetadataBehaviorTest.cs @@ -265,6 +265,8 @@ class MyService : IMyContract Assert.IsNull (behavior.HttpsGetUrl, "HttpsGetUrl"); Assert.IsNotNull (behavior.MetadataExporter, "MetadataExporter #1"); Assert.AreEqual (typeof (WsdlExporter), behavior.MetadataExporter.GetType (), "MetadataExporter #2"); + + Assert.AreEqual ("IMetadataExchange", ServiceMetadataBehavior.MexContractName, "MexContractName"); } } } diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/CallbackBehaviorAttributeTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel/CallbackBehaviorAttributeTest.cs index 46de1fcc76bc8..24700233a1db9 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel/CallbackBehaviorAttributeTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel/CallbackBehaviorAttributeTest.cs @@ -35,6 +35,7 @@ using System.ServiceModel.Description; using System.ServiceModel.Dispatcher; using System.Transactions; +using System.Threading; using NUnit.Framework; namespace MonoTests.System.ServiceModel @@ -124,5 +125,77 @@ public interface IDuplexFoo [OperationContract] void Block (string s); } + + #region "bug #567672" + [Test] + public void CallbackExample1 () + { + //Start service and use net.tcp binding + ServiceHost eventServiceHost = new ServiceHost (typeof (GreetingsService)); + NetTcpBinding tcpBindingpublish = new NetTcpBinding (); + tcpBindingpublish.Security.Mode = SecurityMode.None; + eventServiceHost.AddServiceEndpoint (typeof (IGreetings), tcpBindingpublish, "net.tcp://localhost:8000/GreetingsService"); + eventServiceHost.Open (); + + //Create client proxy + NetTcpBinding clientBinding = new NetTcpBinding (); + clientBinding.Security.Mode = SecurityMode.None; + EndpointAddress ep = new EndpointAddress ("net.tcp://localhost:8000/GreetingsService"); + ClientCallback cb = new ClientCallback (); + IGreetings proxy = DuplexChannelFactory.CreateChannel (new InstanceContext (cb), clientBinding, ep); + + //Call service + proxy.SendMessage (); + + //Wait for callback - sort of hack, but better than using wait handle to possibly block tests. + Thread.Sleep (1000); + + //Cleanup + eventServiceHost.Close (); + + Assert.IsTrue (CallbackSent, "#1"); + Assert.IsTrue (CallbackReceived, "#1"); + } + + public static bool CallbackSent, CallbackReceived; + + //Service implementation + [ServiceBehavior (ConcurrencyMode = ConcurrencyMode.Multiple, InstanceContextMode = InstanceContextMode.Single)] + public class GreetingsService : IGreetings + { + public void SendMessage () + { + //Make a callback + IGreetingsCallback clientCallback = OperationContext.Current.GetCallbackChannel (); + + clientCallback.ShowMessage ("Mono and WCF are GREAT!"); + CallbackBehaviorAttributeTest.CallbackSent = true; + } + } + + // Client callback interface implementation + [CallbackBehavior (ConcurrencyMode = ConcurrencyMode.Reentrant, UseSynchronizationContext = false)] + public class ClientCallback : IGreetingsCallback + { + public void ShowMessage (string message) + { + CallbackBehaviorAttributeTest.CallbackReceived = true; + } + } + + [ServiceContract (CallbackContract = typeof (IGreetingsCallback))] + public interface IGreetings + { + [OperationContract (IsOneWay = true)] + void SendMessage (); + } + + [ServiceContract] + public interface IGreetingsCallback + { + [OperationContract (IsOneWay = true)] + void ShowMessage (string message); + } + #endregion } } diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChangeLog b/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChangeLog index 987d2b8705e62..051c4946d6392 100755 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChangeLog +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChangeLog @@ -1,3 +1,42 @@ +2010-02-05 Atsushi Enomoto + + * NetTcpBindingTest.cs : port 808 is not generally available + for non-privileged users. + +2010-01-25 Atsushi Enomoto + + * ChannelFactory_1Test.cs : added a couple of error check tests for + constructors and CreateChannel() overloads. + +2010-01-22 Atsushi Enomoto + + * ServiceHostTest.cs : add a few more comments. + +2010-01-22 Atsushi Enomoto + + * CallbackBehaviorAttributeTest.cs : enable the test again. + +2010-01-22 Atsushi Enomoto + + * NetTcpBindingTest.cs : enabled connection tests again, as they + got working again (and more importantly, they don't block). + * CallbackBehaviorAttributeTest.cs : on the other hand, disabled + a test so far. It is the only active test && the blocker now. + +2010-01-20 Atsushi Enomoto + + * NetTcpBindingTest.cs : disable connection tests, with analyzed + reason why it's blocking, for each. + +2010-01-13 Atsushi Enomoto + + * EndpointAddressBuilderTest.cs : add usage example test. + +2010-01-08 Atsushi Enomoto + + * CallbackBehaviorAttributeTest.cs : added callback example from + bug #567672. + 2010-01-07 Atsushi Enomoto * ServiceHostBaseTest.cs : another mannerless test here. diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChannelFactory_1Test.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChannelFactory_1Test.cs index ea1ba135f33fa..75e51fd6706aa 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChannelFactory_1Test.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel/ChannelFactory_1Test.cs @@ -65,6 +65,14 @@ public void CreateChannelForClass () new EndpointAddress ("http://localhost:37564")); } + [Test] + public void EndpointAddressAfterCreateChannel () + { + var f = new ChannelFactory (new BasicHttpBinding ()); + f.CreateChannel (new EndpointAddress ("http://localhost:37564"), null); + Assert.IsNull (f.Endpoint.Address, "#1"); + } + [Test] [Ignore ("fails under .NET; I never bothered to fix the test")] public void CtorNullArgsAllowed () @@ -128,9 +136,19 @@ public void ConstructorNullBinding () [Test] public void ConfigEmptyCtor () { + // It has no valid configuration, but goes on. new ChannelFactory (); } + [Test] + [ExpectedException (typeof (InvalidOperationException))] + public void ConfigEmptyCtor2 () + { + var cf = new ChannelFactory (); + // It cannot go on further. + cf.CreateChannel (); + } + [Test] [Ignore ("fails under .NET; I never bothered to fix the test")] public void ConfigCtor () diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/EndpointAddressBuilderTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel/EndpointAddressBuilderTest.cs index 0290c2dd8d35f..afa9619ccaab5 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel/EndpointAddressBuilderTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel/EndpointAddressBuilderTest.cs @@ -27,6 +27,7 @@ // using System; using System.Collections.Generic; +using System.IO; using System.ServiceModel; using System.Text; using System.Xml; @@ -44,5 +45,21 @@ public void ToEndpointAddressWithoutReader () { new EndpointAddressBuilder ().ToEndpointAddress (); } + + [Test] + public void UsageExample () + { + var eb = new EndpointAddressBuilder (); + var dr = XmlDictionaryReader.CreateDictionaryReader (XmlReader.Create (new StringReader (""))); + eb.SetExtensionReader (dr); + Assert.AreEqual (ReadState.EndOfFile, dr.ReadState, "#1"); + var xr = eb.GetReaderAtExtensions (); + xr.ReadOuterXml (); + xr = eb.GetReaderAtExtensions (); // do not return the same XmlReader + Assert.AreEqual (ReadState.Interactive, xr.ReadState, "#2"); + xr.ReadOuterXml (); + eb.SetExtensionReader (null); // allowed + Assert.IsNull (eb.GetReaderAtExtensions (), "#3"); + } } } diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/NetTcpBindingTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel/NetTcpBindingTest.cs index 693c1b26ccf56..1c051a132c185 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel/NetTcpBindingTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel/NetTcpBindingTest.cs @@ -58,33 +58,22 @@ public void DefaultValues () Assert.IsNotNull (tx, "#tx1"); } - // Those connection tests are somehow blocked by some tests - // I disabled recently (see svn history) but while those broken - // tests examine almost nothing, these tests below does, so I - // rather enabled them. - // - // Those tests somehow got broken in Nov. 2009 probably because - // of some underlying net layer and not due to those ignored - // tests though. But those tests leave channels open, so they - // are bad enough to be disabled. - [Test] public void BufferedConnection () { var host = new ServiceHost (typeof (Foo)); - var bindingsvc = new NetTcpBinding (); - bindingsvc.Security.Mode = SecurityMode.None; - host.AddServiceEndpoint (typeof (IFoo), bindingsvc, "net.tcp://localhost/"); + var bindingsvc = new CustomBinding (new BinaryMessageEncodingBindingElement (), new TcpTransportBindingElement ()); + host.AddServiceEndpoint (typeof (IFoo), bindingsvc, "net.tcp://localhost:37564/"); host.Open (TimeSpan.FromSeconds (5)); try { - var bindingcli = new NetTcpBinding (); + var bindingcli = new NetTcpBinding () { TransactionFlow = false }; bindingcli.Security.Mode = SecurityMode.None; - var cli = new ChannelFactory (bindingcli, new EndpointAddress ("net.tcp://localhost/")).CreateChannel (); + var cli = new ChannelFactory (bindingcli, new EndpointAddress ("net.tcp://localhost:37564/")).CreateChannel (); Assert.AreEqual (5, cli.Add (1, 4)); Assert.AreEqual ("monkey science", cli.Join ("monkey", "science")); } finally { host.Close (TimeSpan.FromSeconds (5)); - var t = new TcpListener (808); + var t = new TcpListener (37564); t.Start (); t.Stop (); } @@ -96,21 +85,19 @@ public void BufferedConnection () public void StreamedConnection () { var host = new ServiceHost (typeof (Foo)); - var bindingsvc = new NetTcpBinding (); - bindingsvc.TransferMode = TransferMode.Streamed; - bindingsvc.Security.Mode = SecurityMode.None; - host.AddServiceEndpoint (typeof (IFoo), bindingsvc, "net.tcp://localhost/"); + var bindingsvc = new CustomBinding (new BinaryMessageEncodingBindingElement (), new TcpTransportBindingElement () { TransferMode = TransferMode.Streamed }); + host.AddServiceEndpoint (typeof (IFoo), bindingsvc, "net.tcp://localhost:37564/"); host.Open (TimeSpan.FromSeconds (5)); try { - var bindingcli = new NetTcpBinding (); + var bindingcli = new NetTcpBinding () { TransactionFlow = false }; bindingcli.TransferMode = TransferMode.Streamed; bindingcli.Security.Mode = SecurityMode.None; - var cli = new ChannelFactory (bindingcli, new EndpointAddress ("net.tcp://localhost/")).CreateChannel (); + var cli = new ChannelFactory (bindingcli, new EndpointAddress ("net.tcp://localhost:37564/")).CreateChannel (); Assert.AreEqual (5, cli.Add (1, 4)); Assert.AreEqual ("monkey science", cli.Join ("monkey", "science")); } finally { host.Close (TimeSpan.FromSeconds (5)); - var t = new TcpListener (808); + var t = new TcpListener (37564); t.Start (); t.Stop (); } diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/ServiceHostTest.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel/ServiceHostTest.cs index a469c8279ebd9..c3ef2365e9a75 100644 --- a/mcs/class/System.ServiceModel/Test/System.ServiceModel/ServiceHostTest.cs +++ b/mcs/class/System.ServiceModel/Test/System.ServiceModel/ServiceHostTest.cs @@ -161,7 +161,8 @@ public void AddServiceEndpoint4 () public void AddServiceEndpoint5 () { ServiceHost host = new ServiceHost (typeof (Baz), new Uri ("http://localhost/echo")); - // Full type name is expected here. + + // Full type name is expected here (see AddServiceEndpoint4). host.AddServiceEndpoint ("IBaz", new BasicHttpBinding (), "rel"); } @@ -187,6 +188,7 @@ public void AddServiceEndpointMex () public void AddServiceEndpointMetadataExchange () { ServiceHost host = new ServiceHost (typeof (MyMetadataExchange)); + // strange, but unlike above, it is accepted. The only difference I can see is the binding name. host.AddServiceEndpoint ("IMetadataExchange", new BasicHttpBinding (), "http://localhost:8080"); diff --git a/mcs/class/System.ServiceModel/net_2_1_raw_System.ServiceModel.dll.sources b/mcs/class/System.ServiceModel/net_2_1_raw_System.ServiceModel.dll.sources index 7e08332a1ce92..4cd367129bbc5 100755 --- a/mcs/class/System.ServiceModel/net_2_1_raw_System.ServiceModel.dll.sources +++ b/mcs/class/System.ServiceModel/net_2_1_raw_System.ServiceModel.dll.sources @@ -74,6 +74,7 @@ System.ServiceModel.Channels/CustomBinding.cs System.ServiceModel.Channels/FaultConverter.cs System.ServiceModel.Channels/HtmlizedException.cs System.ServiceModel.Channels/HttpChannelFactory.cs +System.ServiceModel.Channels/HttpCookieContainerBindingElement.cs System.ServiceModel.Channels/HttpRequestChannel.cs System.ServiceModel.Channels/HttpRequestMessageProperty.cs System.ServiceModel.Channels/HttpResponseMessageProperty.cs @@ -133,6 +134,8 @@ System.ServiceModel.Description/ContractDescription.cs System.ServiceModel.Description/ContractDescriptionGenerator.cs System.ServiceModel.Description/FaultDescription.cs System.ServiceModel.Description/FaultDescriptionCollection.cs +System.ServiceModel.Description/IEndpointBehavior.cs +System.ServiceModel.Description/IOperationBehavior.cs System.ServiceModel.Description/MessageBodyDescription.cs System.ServiceModel.Description/MessageDescription.cs System.ServiceModel.Description/MessageDescriptionCollection.cs @@ -148,6 +151,7 @@ System.ServiceModel.Description/ServiceEndpoint.cs System.ServiceModel.Dispatcher/BaseMessagesFormatter.cs System.ServiceModel.Dispatcher/ClientOperation.cs System.ServiceModel.Dispatcher/ClientRuntime.cs +System.ServiceModel.Dispatcher/FaultContractInfo.cs System.ServiceModel.Dispatcher/IChannelInitializer.cs System.ServiceModel.Dispatcher/IClientMessageFormatter.cs System.ServiceModel.Dispatcher/IClientMessageInspector.cs @@ -176,6 +180,7 @@ System.ServiceModel/DefaultCommunicationTimeouts.cs System.ServiceModel/Dummy.cs System.ServiceModel/EndpointAddress.cs System.ServiceModel/EndpointAddress10.cs +System.ServiceModel/EndpointAddressBuilder.cs System.ServiceModel/EndpointNotFoundException.cs System.ServiceModel/EnvelopeVersion.cs System.ServiceModel/ExceptionDetail.cs