-
Notifications
You must be signed in to change notification settings - Fork 5.3k
Description
Assume we have a program which is allocating fixed amount of memory(~200MB) in a tight loop with portions of 200KB in multiple threads:
using System.Linq;
using System.Threading;
class Program
{
public static void Main(string[] args)
{
var threadsCount = args.Any() ? int.Parse(args[0]) : 4;
var waitHandles = new WaitHandle[threadsCount];
int counter = 1024;
for (int i = 0; i != threadsCount; ++i)
{
var waitHandle = new AutoResetEvent(false);
var thread = new Thread(() =>
{
while (Interlocked.Decrement(ref counter) > 0)
{
var _ = new byte[200 * 1024];
}
waitHandle.Set();
});
thread.Start();
waitHandles[i] = waitHandle;
}
WaitHandle.WaitAll(waitHandles);
}
}
If I run this program on .NET Core 5 (Windows 10) with one thread I'll get 1023 events with 204 848 bytes allocated each which is expected. Sum of allocation sizes column: ~210MB (see PerfView status bar in the bottom). If I ran multiple times - I get same numbers:
However If I run this program with 4 or 8 threads, allocation sizes will start to differ and total sum will not be equal to 200MB. It fluctuates between 70(Release configuration) to 360MB. Which can't be right:
Should there be thread synchronization on this allocation size counter or synchronization is not viable option because of low overhead requirement?

