Skip to content

AsynchronousWorker sometimes runs on the main thread #204

@George-Shaw

Description

@George-Shaw

If DogStatsdService is configured from a task that uses a non-default task scheduler, AsynchronousWorker uses that task scheduler for its worker tasks. This can result in worker tasks blocking threads the application uses, such as the application's main thread. AsynchronousWorker should explicitly use TaskScheduler.Default instead of inheriting the current task's scheduler.

Minimal code to reproduce this in a Windows Forms application. This schedules a short-lived task on the main thread for configuring DogStatsdService. A long-lived worker task ends up on the main thread, causing the application to freeze:

public Form1()
{
	// Initialise DogStatsd on the main thread _after_ the constructor returns.
	Task.Factory.StartNew( () => {
		dogStatsdSvc = new DogStatsdService();

		dogStatsdSvc.Configure( new StatsdConfig()
		{
			StatsdServerName = "localhost",
			StatsdPort = 8125
		} );
	}, CancellationToken.None, TaskCreationOptions.None, TaskScheduler.FromCurrentSynchronizationContext() );
}

The code that creates the worker tasks in AsynchronousWorker (line 39):

_workers.Add(Task.Factory.StartNew(() => Dequeue(), TaskCreationOptions.LongRunning));

I believe this should be changed to:

_workers.Add(Task.Factory.StartNew(() => Dequeue(), CancellationToken.None, TaskCreationOptions.LongRunning, TaskScheduler.Default));

Using Task.Run would be even better if you don't need compatibility with .NET versions before 4.5.

For more information on the issues of using Task.Factory.StartNew without specifying a task scheduler, see https://blog.stephencleary.com/2013/08/startnew-is-dangerous.html. Search for and read from "Confusing default scheduler".

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions