Alexandre Julliard : shell32: Store an id in change notifications to avoid invalid pointer conversions.
Alexandre Julliard
julliard at winehq.org
Fri Apr 9 11:49:55 CDT 2010
Module: wine
Branch: master
Commit: 8bfc89ee7cd2ae8a432ce6aa58b956e24aa6f6e7
URL: http://source.winehq.org/git/wine.git/?a=commit;h=8bfc89ee7cd2ae8a432ce6aa58b956e24aa6f6e7
Author: Alexandre Julliard <julliard at winehq.org>
Date: Fri Apr 9 14:42:29 2010 +0200
shell32: Store an id in change notifications to avoid invalid pointer conversions.
---
dlls/shell32/changenotify.c | 56 +++++++++++++++++++++---------------------
1 files changed, 28 insertions(+), 28 deletions(-)
diff --git a/dlls/shell32/changenotify.c b/dlls/shell32/changenotify.c
index 3e79b2e..95f2e42 100644
--- a/dlls/shell32/changenotify.c
+++ b/dlls/shell32/changenotify.c
@@ -54,10 +54,11 @@ typedef struct _NOTIFICATIONLIST
LONG wSignalledEvent; /* event that occurred */
DWORD dwFlags; /* client flags */
LPCITEMIDLIST pidlSignaled; /*pidl of the path that caused the signal*/
-
+ ULONG id;
} NOTIFICATIONLIST, *LPNOTIFICATIONLIST;
static struct list notifications = LIST_INIT( notifications );
+static LONG next_id;
#define SHCNE_NOITEMEVENTS ( \
SHCNE_ASSOCCHANGED )
@@ -117,15 +118,6 @@ static const char * NodeName(const NOTIFICATIONLIST *item)
return str;
}
-static LPNOTIFICATIONLIST FindNode( HANDLE hitem )
-{
- LPNOTIFICATIONLIST ptr;
- LIST_FOR_EACH_ENTRY( ptr, ¬ifications, NOTIFICATIONLIST, entry )
- if( ptr == hitem )
- return ptr;
- return NULL;
-}
-
static void DeleteNode(LPNOTIFICATIONLIST item)
{
UINT i;
@@ -195,6 +187,7 @@ SHChangeNotifyRegister(
item->wEventMask = wEventMask;
item->wSignalledEvent = 0;
item->dwFlags = fSources;
+ item->id = InterlockedIncrement( &next_id );
TRACE("new node: %s\n", NodeName( item ));
@@ -204,7 +197,7 @@ SHChangeNotifyRegister(
LeaveCriticalSection(&SHELL32_ChangenotifyCS);
- return (ULONG)item;
+ return item->id;
}
/*************************************************************************
@@ -218,13 +211,17 @@ BOOL WINAPI SHChangeNotifyDeregister(ULONG hNotify)
EnterCriticalSection(&SHELL32_ChangenotifyCS);
- node = FindNode((HANDLE)hNotify);
- if( node )
- DeleteNode(node);
-
+ LIST_FOR_EACH_ENTRY( node, ¬ifications, NOTIFICATIONLIST, entry )
+ {
+ if (node->id == hNotify)
+ {
+ DeleteNode( node );
+ LeaveCriticalSection(&SHELL32_ChangenotifyCS);
+ return TRUE;
+ }
+ }
LeaveCriticalSection(&SHELL32_ChangenotifyCS);
-
- return node?TRUE:FALSE;
+ return FALSE;
}
/*************************************************************************
@@ -429,22 +426,25 @@ HANDLE WINAPI SHChangeNotification_Lock(
/* EnterCriticalSection(&SHELL32_ChangenotifyCS); */
- node = FindNode( hChange );
- if( node )
+ LIST_FOR_EACH_ENTRY( node, ¬ifications, NOTIFICATIONLIST, entry )
{
- idlist = SHAlloc( sizeof(LPCITEMIDLIST *) * node->cidl );
- for(i=0; i<node->cidl; i++)
- idlist[i] = node->pidlSignaled;
- *lpwEventId = node->wSignalledEvent;
- *lppidls = (LPITEMIDLIST*)idlist;
- node->wSignalledEvent = 0;
+ if (node == hChange)
+ {
+ idlist = SHAlloc( sizeof(LPCITEMIDLIST *) * node->cidl );
+ for(i=0; i<node->cidl; i++)
+ idlist[i] = node->pidlSignaled;
+ *lpwEventId = node->wSignalledEvent;
+ *lppidls = (LPITEMIDLIST*)idlist;
+ node->wSignalledEvent = 0;
+ /* LeaveCriticalSection(&SHELL32_ChangenotifyCS); */
+ return node;
+ }
}
- else
- ERR("Couldn't find %p\n", hChange );
+ ERR("Couldn't find %p\n", hChange );
/* LeaveCriticalSection(&SHELL32_ChangenotifyCS); */
- return node;
+ return 0;
}
/*************************************************************************
More information about the wine-cvs
mailing list