summaryrefslogtreecommitdiffstats
path: root/modules/mono/glue/Managed/Files/GodotTaskScheduler.cs
diff options
context:
space:
mode:
authorIgnacio Etcheverry <neikeq@users.noreply.github.com>2018-09-12 22:08:54 +0200
committerGitHub <noreply@github.com>2018-09-12 22:08:54 +0200
commit8704b7787624da98cece35c1b8b8e51bde709488 (patch)
tree398ab2ee1e88e3b853c6157458362dced14d64da /modules/mono/glue/Managed/Files/GodotTaskScheduler.cs
parent4cd3dd821932660a7d89d90da7626fa46c07ac39 (diff)
parent995a40e8efa9f7a868a6706e30c476305e16180b (diff)
downloadredot-engine-8704b7787624da98cece35c1b8b8e51bde709488.tar.gz
Merge pull request #22007 from neikeq/<name_of_your_new_branch>
Move modules/mono/glue/cs_files to modules/mono/glue/Managed/Files
Diffstat (limited to 'modules/mono/glue/Managed/Files/GodotTaskScheduler.cs')
-rw-r--r--modules/mono/glue/Managed/Files/GodotTaskScheduler.cs94
1 files changed, 94 insertions, 0 deletions
diff --git a/modules/mono/glue/Managed/Files/GodotTaskScheduler.cs b/modules/mono/glue/Managed/Files/GodotTaskScheduler.cs
new file mode 100644
index 0000000000..9a40fef5a9
--- /dev/null
+++ b/modules/mono/glue/Managed/Files/GodotTaskScheduler.cs
@@ -0,0 +1,94 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace Godot
+{
+ public class GodotTaskScheduler : TaskScheduler
+ {
+ private GodotSynchronizationContext Context { get; set; }
+ private readonly LinkedList<Task> _tasks = new LinkedList<Task>();
+
+ public GodotTaskScheduler()
+ {
+ Context = new GodotSynchronizationContext();
+ SynchronizationContext.SetSynchronizationContext(Context);
+ }
+
+ protected sealed override void QueueTask(Task task)
+ {
+ lock (_tasks)
+ {
+ _tasks.AddLast(task);
+ }
+ }
+
+ protected sealed override bool TryExecuteTaskInline(Task task, bool taskWasPreviouslyQueued)
+ {
+ if (SynchronizationContext.Current != Context)
+ {
+ return false;
+ }
+
+ if (taskWasPreviouslyQueued)
+ {
+ TryDequeue(task);
+ }
+
+ return TryExecuteTask(task);
+ }
+
+ protected sealed override bool TryDequeue(Task task)
+ {
+ lock (_tasks)
+ {
+ return _tasks.Remove(task);
+ }
+ }
+
+ protected sealed override IEnumerable<Task> GetScheduledTasks()
+ {
+ lock (_tasks)
+ {
+ return _tasks.ToArray();
+ }
+ }
+
+ public void Activate()
+ {
+ ExecuteQueuedTasks();
+ Context.ExecutePendingContinuations();
+ }
+
+ private void ExecuteQueuedTasks()
+ {
+ while (true)
+ {
+ Task task;
+
+ lock (_tasks)
+ {
+ if (_tasks.Any())
+ {
+ task = _tasks.First.Value;
+ _tasks.RemoveFirst();
+ }
+ else
+ {
+ break;
+ }
+ }
+
+ if (task != null)
+ {
+ if (!TryExecuteTask(task))
+ {
+ throw new InvalidOperationException();
+ }
+ }
+ }
+ }
+ }
+}