// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
//
-#if NET_2_0 && SECURITY_DEP
+#if SECURITY_DEP
using System.Threading;
namespace System.Net {
HttpListenerContext context;
object locker = new object ();
ListenerAsyncResult forward;
+ internal bool EndCalled;
+ internal bool InGet;
public ListenerAsyncResult (AsyncCallback cb, object state)
{
this.state = state;
}
- internal void Complete (string error)
+ internal void Complete (Exception exc)
{
if (forward != null) {
- forward.Complete (error);
+ forward.Complete (exc);
return;
}
- //FIXME: error_code?
- exception = new HttpListenerException (0, error);
+ exception = exc;
+ if (InGet && (exc is ObjectDisposedException))
+ exception = new HttpListenerException (500, "Listener closed");
lock (locker) {
completed = true;
if (handle != null)
handle.Set ();
if (cb != null)
- ThreadPool.QueueUserWorkItem (InvokeCallback, this);
+ ThreadPool.UnsafeQueueUserWorkItem (InvokeCB, this);
}
}
+ static WaitCallback InvokeCB = new WaitCallback (InvokeCallback);
static void InvokeCallback (object o)
{
ListenerAsyncResult ares = (ListenerAsyncResult) o;
if (ares.forward != null) {
- ares.forward.cb (ares);
+ InvokeCallback (ares.forward);
return;
}
- ares.cb (ares);
+ try {
+ ares.cb (ares);
+ } catch {
+ }
}
internal void Complete (HttpListenerContext context)
this.synch = synch;
this.context = context;
lock (locker) {
- completed = true;
- if (handle != null)
- handle.Set ();
-
AuthenticationSchemes schemes = context.Listener.SelectAuthenticationScheme (context);
if ((schemes == AuthenticationSchemes.Basic || context.Listener.AuthenticationSchemes == AuthenticationSchemes.Negotiate) && context.Request.Headers ["Authorization"] == null) {
- context.Listener.InternalEndGetContext (this);
context.Response.StatusCode = 401;
- context.Response.Headers ["WWW-Authenticate"] = schemes + " realm=\"\"";
+ context.Response.Headers ["WWW-Authenticate"] = schemes + " realm=\"" + context.Listener.Realm + "\"";
context.Response.OutputStream.Close ();
IAsyncResult ares = context.Listener.BeginGetContext (cb, state);
this.forward = (ListenerAsyncResult) ares;
- if (handle != null)
- forward.handle = handle;
+ lock (forward.locker) {
+ if (handle != null)
+ forward.handle = handle;
+ }
ListenerAsyncResult next = forward;
for (int i = 0; next.forward != null; i++) {
if (i > 20)
- Complete ("Too many authentication errors");
+ Complete (new HttpListenerException (400, "Too many authentication errors"));
next = next.forward;
}
- } else if (cb != null)
- ThreadPool.QueueUserWorkItem (InvokeCallback, this);
+ } else {
+ completed = true;
+ this.synch = false;
+
+ if (handle != null)
+ handle.Set ();
+
+ if (cb != null)
+ ThreadPool.UnsafeQueueUserWorkItem (InvokeCB, this);
+ }
}
}