Browse Source

Assume all task cancellations are unexpected even if no exception was captured, unless stop is directly invoked

tags/docs-0.9
RogueException 9 years ago
parent
commit
33a2e1858d
5 changed files with 23 additions and 19 deletions
  1. +2
    -2
      src/Discord.Net/DiscordClient.cs
  2. +1
    -1
      src/Discord.Net/Net/WebSockets/GatewaySocket.cs
  3. +2
    -2
      src/Discord.Net/Net/WebSockets/WS4NetEngine.cs
  4. +3
    -3
      src/Discord.Net/Net/WebSockets/WebSocket.cs
  5. +15
    -11
      src/Discord.Net/TaskManager.cs

+ 2
- 2
src/Discord.Net/DiscordClient.cs View File

@@ -189,7 +189,7 @@ namespace Discord
} }
catch (Exception ex) catch (Exception ex)
{ {
_taskManager.SignalError(ex, true);
_taskManager.SignalError(ex);
throw; throw;
} }
} }
@@ -264,7 +264,7 @@ namespace Discord
} }


/// <summary> Disconnects from the Discord server, canceling any pending requests. </summary> /// <summary> Disconnects from the Discord server, canceling any pending requests. </summary>
public Task Disconnect() => _taskManager.Stop();
public Task Disconnect() => _taskManager.Stop(true);
private async Task Cleanup() private async Task Cleanup()
{ {
State = ConnectionState.Disconnecting; State = ConnectionState.Disconnecting;


+ 1
- 1
src/Discord.Net/Net/WebSockets/GatewaySocket.cs View File

@@ -63,7 +63,7 @@ namespace Discord.Net.WebSockets
} }
catch (OperationCanceledException) { } catch (OperationCanceledException) { }
} }
public Task Disconnect() => _taskManager.Stop();
public Task Disconnect() => _taskManager.Stop(true);


protected override async Task Run() protected override async Task Run()
{ {


+ 2
- 2
src/Discord.Net/Net/WebSockets/WS4NetEngine.cs View File

@@ -76,7 +76,7 @@ namespace Discord.Net.WebSockets


private void OnWebSocketError(object sender, ErrorEventArgs e) private void OnWebSocketError(object sender, ErrorEventArgs e)
{ {
_taskManager.SignalError(e.Exception, isUnexpected: true);
_taskManager.SignalError(e.Exception);
_waitUntilConnect.Set(); _waitUntilConnect.Set();
} }
private void OnWebSocketClosed(object sender, EventArgs e) private void OnWebSocketClosed(object sender, EventArgs e)
@@ -86,7 +86,7 @@ namespace Discord.Net.WebSockets
ex = new WebSocketException((e as ClosedEventArgs).Code, (e as ClosedEventArgs).Reason); ex = new WebSocketException((e as ClosedEventArgs).Code, (e as ClosedEventArgs).Reason);
else else
ex = new Exception($"Connection lost"); ex = new Exception($"Connection lost");
_taskManager.SignalError(ex, isUnexpected: true);
_taskManager.SignalError(ex);
_waitUntilConnect.Set(); _waitUntilConnect.Set();
} }
private void OnWebSocketOpened(object sender, EventArgs e) private void OnWebSocketOpened(object sender, EventArgs e)


+ 3
- 3
src/Discord.Net/Net/WebSockets/WebSocket.cs View File

@@ -95,7 +95,7 @@ namespace Discord.Net.WebSockets
} }
catch (Exception ex) catch (Exception ex)
{ {
_taskManager.SignalError(ex, true);
_taskManager.SignalError(ex);
throw; throw;
} }
} }
@@ -111,7 +111,7 @@ namespace Discord.Net.WebSockets
} }
catch (Exception ex) catch (Exception ex)
{ {
_taskManager.SignalError(ex, true);
_taskManager.SignalError(ex);
} }
} }


@@ -132,7 +132,7 @@ namespace Discord.Net.WebSockets
Logger.Info("Disconnected"); Logger.Info("Disconnected");
else else
Logger.Error("Disconnected", ex); Logger.Error("Disconnected", ex);
OnDisconnected(_taskManager.WasUnexpected, _taskManager.Exception);
OnDisconnected(!_taskManager.WasStopExpected, _taskManager.Exception);
} }
State = ConnectionState.Disconnected; State = ConnectionState.Disconnected;
} }


+ 15
- 11
src/Discord.Net/TaskManager.cs View File

@@ -16,8 +16,8 @@ namespace Discord
private CancellationTokenSource _cancelSource; private CancellationTokenSource _cancelSource;
private Task _task; private Task _task;


public bool WasUnexpected => _wasStopUnexpected;
private bool _wasStopUnexpected;
public bool WasStopExpected => _wasStopExpected;
private bool _wasStopExpected;


public Exception Exception => _stopReason?.SourceException; public Exception Exception => _stopReason?.SourceException;
private ExceptionDispatchInfo _stopReason; private ExceptionDispatchInfo _stopReason;
@@ -53,7 +53,7 @@ namespace Discord
continue; //Another thread sneaked in and started this manager before we got a lock, loop and try again continue; //Another thread sneaked in and started this manager before we got a lock, loop and try again


_stopReason = null; _stopReason = null;
_wasStopUnexpected = false;
_wasStopExpected = false;


Task[] tasksArray = tasks.ToArray(); Task[] tasksArray = tasks.ToArray();
Task<Task> anyTask = Task.WhenAny(tasksArray); Task<Task> anyTask = Task.WhenAny(tasksArray);
@@ -66,7 +66,7 @@ namespace Discord


//Signal the rest of the tasks to stop //Signal the rest of the tasks to stop
if (firstTask.Exception != null) if (firstTask.Exception != null)
SignalError(firstTask.Exception, true);
SignalError(firstTask.Exception);
else else
SignalStop(); SignalStop();


@@ -84,10 +84,13 @@ namespace Discord
} }
} }


public void SignalStop()
public void SignalStop(bool isExpected = false)
{ {
lock (_lock) lock (_lock)
{ {
if (isExpected)
_wasStopExpected = true;

if (_task == null) return; //Are we running? if (_task == null) return; //Are we running?
if (_cancelSource.IsCancellationRequested) return; if (_cancelSource.IsCancellationRequested) return;


@@ -95,11 +98,14 @@ namespace Discord
_cancelSource.Cancel(); _cancelSource.Cancel();
} }
} }
public Task Stop()
public Task Stop(bool isExpected = false)
{ {
Task task; Task task;
lock (_lock) lock (_lock)
{ {
if (isExpected)
_wasStopExpected = true;

//Cache the task so we still have something to await if Cleanup is run really quickly //Cache the task so we still have something to await if Cleanup is run really quickly
task = _task; task = _task;
if (task == null) return TaskHelper.CompletedTask; //Are we running? if (task == null) return TaskHelper.CompletedTask; //Are we running?
@@ -111,19 +117,18 @@ namespace Discord
return task; return task;
} }


public void SignalError(Exception ex, bool isUnexpected = true)
public void SignalError(Exception ex)
{ {
lock (_lock) lock (_lock)
{ {
if (_stopReason != null) return; if (_stopReason != null) return;


_stopReason = ExceptionDispatchInfo.Capture(ex); _stopReason = ExceptionDispatchInfo.Capture(ex);
_wasStopUnexpected = isUnexpected;
if (_cancelSource != null) if (_cancelSource != null)
_cancelSource.Cancel(); _cancelSource.Cancel();
} }
} }
public Task Error(Exception ex, bool isUnexpected = true)
public Task Error(Exception ex)
{ {
Task task; Task task;
lock (_lock) lock (_lock)
@@ -135,7 +140,6 @@ namespace Discord
if (_cancelSource.IsCancellationRequested) return task; if (_cancelSource.IsCancellationRequested) return task;


_stopReason = ExceptionDispatchInfo.Capture(ex); _stopReason = ExceptionDispatchInfo.Capture(ex);
_wasStopUnexpected = isUnexpected;
if (_cancelSource != null) if (_cancelSource != null)
_cancelSource.Cancel(); _cancelSource.Cancel();
} }
@@ -153,7 +157,7 @@ namespace Discord
lock (_lock) lock (_lock)
{ {
_stopReason = null; _stopReason = null;
_wasStopUnexpected = false;
_wasStopExpected = false;
} }
} }
} }


Loading…
Cancel
Save