Sami
Sami

Reputation: 1389

Synchronizing multiple threads

I have a multi-threaded environment in .NET that needs to communicate to a library. The library has some limitations and therefore cannot work correctly with multi-threaded environments. I need a way to solve this issue by making middle layer that the multi-threaded environment communicates with and then calls the library. I made a solution that solved the problem but I am not convinced that it is the best one. I created an asynchronous thread that has a run method. The run method is in infinite loop that checks what is the current task (a parameter that I set) and executes the corresponding method.

As I said, I am not convinced at all with this solution but it does the job correctly. So please inform me if there is a better one to solve it (especially if it is related to C#).

Just as a side note, the limitation isn't due to multiple threads that are working at the same time and causing data corruption. I need the exact same thread to do everything (depends on thread id).

Upvotes: 2

Views: 1145

Answers (1)

dtb
dtb

Reputation: 217401

Have a look at the Task Parallel Library.

I recommend you implement a custom TaskScheduler that schedules all tasks on the same thread. You can use the scheduler to schedule a Task (no result value) or a Task<T> (result of type T).

You can use a BlockingCollection<Task> wrapping a ConcurrentQueue<Task> to implement the scheduler.

For example, assuming that your library exposes a function MakeCoffee, you could create a class CoffeeMachine that provides a matching wrapper method and schedules the task of calling the library on the custom scheduler:

public class CoffeeMachine
{
    private readonly TaskScheduler scheduler;

    public CoffeeMachine()
    {
        this.scheduler = new SingleThreadTaskScheduler();
    }

    public Task<Coffee> MakeCoffeeAsync()
    {
        return Task.Factory.StartNew<Coffee>(
            this.MakeCoffee,
            CancellationToken.None,
            TaskCreationOptions.None,
            this.scheduler);
    }

    private Coffee MakeCoffee()
    {
        // this method will always execute on the same thread
    }
}

Usage:

CoffeeMachine machine = new CoffeeMachine();

Task<Coffee> task = machine.MakeCoffeeAsync();   // start task

task.Wait();                                     // wait for task to complete
Drink(task.Result);                              // use result

Upvotes: 2

Related Questions