I have a long running process that sends data to the other machine. But this data is received in chunks (like a set of 100 packets, then delay of minimum 10 seconds).
I started the sending function on a separate thread using
Task.Run(() => { SendPackets(); });
The packets to be sent are queued in a Queue<Packet>
object by some other function.
In SendPackets()
I am using a while loop to retrieve and send (asynchronously) all items available in the queue.
void SendPackets()
{
while(isRunning)
{
while(thePacketQueue.Count > 0)
{
Packet pkt = thePacketQueue.Dequeue();
BeginSend(pkt, callback); // Actual code to send data over asynchronously
}
Task.Delay(1000); // <---- My question lies here
}
}
All the locks are in place!
My question is, when I use Task.Delay
, is it possible then the next cycle may be executed by a thread different from the current one?
Is there any other approach, where instead of specifying delay for 1 second, I can use something like ManualResetEvent
, and what would be the respective code (I have no idea how to use the ManualResetEvent
etc.
Also, I am new to async/await and TPL, so kindly bear with my ignorance.
TIA.
My question is, when I use Task.Delay, is it possible then the next cycle may be executed by a thread different from the current one?
Not with the code you've got, because that code is buggy. It won't actually delay between cycles at all. It creates a task that will complete in a second, but then ignores that task. Your code should be:
await Task.Delay(1000);
or potentially:
await Task.Delay(1000).ConfigureAwait(false);
With the second piece of code, that can absolutely run each cycle on a different thread. With the first piece of code, it will depend on the synchronization context. If you were running in a synchronization context with thread affinity (e.g. you're calling this from the UI thread of a WPF or WinForms app) then the async method will continue on the same thread after the delay completes. If you're running without a synchronization context, or in a synchronization context that doesn't just use one thread, then again it could run each cycle in a different thread.
As you're starting this code with Task.Run
, you won't have a synchronization context - but it's worth being aware that the same piece of code could behave differently when run in a different way.
As a side note, it's not clear what's adding items to thePacketQueue
, but unless that's a concurrent collection (e.g. ConcurrentQueue
), you may well have a problem there too.