public unsafe void InterlockedTest2() { const uint max = 10; // Initialize the list header to a MEMORY_ALLOCATION_ALIGNMENT boundary. InitializeSListHead(out var listHead); // Create 10 item list in memory. var items = new IntPtr[max]; for (var Count = 0U; Count < max; Count += 1) { items[Count] = new PROGRAM_ITEM { ItemEntry = new SLIST_ENTRY { Next = Count == 0 ? IntPtr.Zero : items[Count - 1] }, Signature = Count + 1 }.StructureToPtr(Marshal.AllocHGlobal, out _); } // Add list and check Assert.That(InterlockedPushListSListEx(listHead, items[0], items[max - 1], max), Is.EqualTo(IntPtr.Zero)); Assert.That(QueryDepthSList(listHead), Is.EqualTo(max)); // Flush the list and verify that the items are gone. Assert.That(InterlockedFlushSList(listHead), Is.EqualTo(items[0])); Assert.That(InterlockedPopEntrySList(listHead), Is.EqualTo(IntPtr.Zero)); // Free items for (var Count = 0U; Count < max; Count += 1) { Marshal.FreeHGlobal(items[Count]); } }
public unsafe void InterlockedTest() { const uint max = 10; // Initialize the list header to a MEMORY_ALLOCATION_ALIGNMENT boundary. InitializeSListHead(out var listHead); // Insert 10 items into the list. for (var Count = 1U; Count <= max; Count += 1) { var pProgramItem = new PROGRAM_ITEM { Signature = Count }.StructureToPtr(Marshal.AllocHGlobal, out _); InterlockedPushEntrySList(listHead, pProgramItem); } Assert.That(QueryDepthSList(listHead), Is.EqualTo(max)); // Remove 10 items from the list and display the signature. for (var Count = max; Count >= 1; Count -= 1) { var pListEntry = InterlockedPopEntrySList(listHead); var programItem = pListEntry.ToNullableStructure <PROGRAM_ITEM>(); if (!programItem.HasValue) { Assert.Fail("NULL from InterlockedPopEntrySList"); } Assert.That(Count, Is.EqualTo(programItem.Value.Signature)); Marshal.FreeHGlobal(pListEntry); } // Flush the list and verify that the items are gone. Assert.That(InterlockedFlushSList(listHead), Is.EqualTo(IntPtr.Zero)); Assert.That(InterlockedPopEntrySList(listHead), Is.EqualTo(IntPtr.Zero)); }