From 0669a8aca2dec4eaf6632e368832a8aec1c48ffd Mon Sep 17 00:00:00 2001 From: Daniel Lehman Date: Tue, 22 Oct 2013 22:47:26 -0700 Subject: [PATCH] kernel32: Don't use depth in RtlInterlockedFlushSList. Depth wraps around at 65536 but list supports more elements. --- dlls/kernel32/tests/sync.c | 18 +++++++++++++++++- dlls/ntdll/rtl.c | 4 ++-- 2 files changed, 19 insertions(+), 3 deletions(-) diff --git a/dlls/kernel32/tests/sync.c b/dlls/kernel32/tests/sync.c index b98d7c44297..84c44e04569 100644 --- a/dlls/kernel32/tests/sync.c +++ b/dlls/kernel32/tests/sync.c @@ -244,8 +244,9 @@ static void test_slist(void) } item1, item2, item3, *pitem; SLIST_HEADER slist_header; - PSLIST_ENTRY entry; + PSLIST_ENTRY entry, next; USHORT size; + int i; VOID (WINAPI *pInitializeSListHead)(PSLIST_HEADER); USHORT (WINAPI *pQueryDepthSList)(PSLIST_HEADER); @@ -323,6 +324,21 @@ static void test_slist(void) } ok(((struct item*)entry)->value == 2, "item 2 not in front of list\n"); ok(((struct item*)entry->Next)->value == 1, "item 1 not at the back of list\n"); + + for (i = 0; i < 65536; i++) + { + entry = HeapAlloc(GetProcessHeap(), 0, sizeof(*entry)); + pInterlockedPushEntrySList(&slist_header, entry); + } + + entry = pInterlockedFlushSList(&slist_header); + ok(entry != NULL, "not flushed\n"); + while (entry) + { + next = entry->Next; + HeapFree(GetProcessHeap(), 0, entry); + entry = next; + } } static void test_event(void) diff --git a/dlls/ntdll/rtl.c b/dlls/ntdll/rtl.c index abf2ba8345c..8f6f386e45f 100644 --- a/dlls/ntdll/rtl.c +++ b/dlls/ntdll/rtl.c @@ -1080,7 +1080,7 @@ PSLIST_ENTRY WINAPI RtlInterlockedFlushSList(PSLIST_HEADER list) SLIST_HEADER old, new; #ifdef _WIN64 - if (!list->Header16.Depth) return NULL; + if (!list->Header16.NextEntry) return NULL; new.s.Alignment = new.s.Region = 0; new.Header16.HeaderType = 1; /* we use the 16-byte header */ do @@ -1090,7 +1090,7 @@ PSLIST_ENTRY WINAPI RtlInterlockedFlushSList(PSLIST_HEADER list) } while (!interlocked_cmpxchg128((__int64 *)list, new.s.Region, new.s.Alignment, (__int64 *)&old)); return (SLIST_ENTRY *)((ULONG_PTR)old.Header16.NextEntry << 4); #else - if (!list->s.Depth) return NULL; + if (!list->s.Next.Next) return NULL; new.Alignment = 0; do { -- 2.11.4.GIT