From 050435840b523bd711936cfe385ad6f6cb286613 Mon Sep 17 00:00:00 2001
From: Juergen Schmied <juergen.schmied@metronet.de>
Date: Sun, 15 Aug 1999 14:26:30 +0000
Subject: [PATCH] Protect cache with critical section. Removed hack to load
 icons from external shell32.dll.

---
 dlls/shell32/iconcache.c | 115 ++++++++++++++++++++++-----------------
 1 file changed, 64 insertions(+), 51 deletions(-)

diff --git a/dlls/shell32/iconcache.c b/dlls/shell32/iconcache.c
index e5d3f37e919..14bd6b051b8 100644
--- a/dlls/shell32/iconcache.c
+++ b/dlls/shell32/iconcache.c
@@ -457,6 +457,9 @@ typedef struct
 	DWORD dwAccessTime;
 } SIC_ENTRY, * LPSIC_ENTRY;
 
+static HDPA		sic_hdpa = 0;
+static CRITICAL_SECTION	SHELL32_SicCS;
+
 /*****************************************************************************
  * SIC_CompareEntrys			[called by comctl32.dll]
  *
@@ -482,7 +485,7 @@ INT CALLBACK SIC_CompareEntrys( LPVOID p1, LPVOID p2, LPARAM lparam)
  */
 static INT SIC_IconAppend (LPCSTR sSourceFile, INT dwSourceIndex, HICON hSmallIcon, HICON hBigIcon)
 {	LPSIC_ENTRY lpsice;
-	INT index, index1;
+	INT ret, index, index1;
 	
 	TRACE("%s %i %x %x\n", sSourceFile, dwSourceIndex, hSmallIcon ,hBigIcon);
 
@@ -491,22 +494,29 @@ static INT SIC_IconAppend (LPCSTR sSourceFile, INT dwSourceIndex, HICON hSmallIc
 	lpsice->sSourceFile = HEAP_strdupA (GetProcessHeap(), 0, PathFindFilenameA(sSourceFile));
 	lpsice->dwSourceIndex = dwSourceIndex;
 	
+	EnterCriticalSection(&SHELL32_SicCS);
+
 	index = pDPA_InsertPtr(sic_hdpa, 0x7fff, lpsice);
 	if ( INVALID_INDEX == index )
-	{ SHFree(lpsice);
-	  return INVALID_INDEX;
+	{
+	  SHFree(lpsice);
+	  ret = INVALID_INDEX;
 	}
+	else
+	{
+	  index = pImageList_AddIcon (ShellSmallIconList, hSmallIcon);
+	  index1= pImageList_AddIcon (ShellBigIconList, hBigIcon);
 
-	index = pImageList_AddIcon (ShellSmallIconList, hSmallIcon);
-	index1= pImageList_AddIcon (ShellBigIconList, hBigIcon);
-
-	if (index!=index1)
-	{ FIXME("iconlists out of sync 0x%x 0x%x\n", index, index1);
+	  if (index!=index1)
+	  {
+	    FIXME("iconlists out of sync 0x%x 0x%x\n", index, index1);
+	  }
+	  lpsice->dwListIndex = index;
+	  ret = lpsice->dwListIndex;
 	}
-	lpsice->dwListIndex = index;
-	
-	return lpsice->dwListIndex;
-	
+
+	LeaveCriticalSection(&SHELL32_SicCS);
+	return ret;	
 }
 /****************************************************************************
  * SIC_LoadIcon				[internal]
@@ -523,7 +533,8 @@ static INT SIC_LoadIcon (LPCSTR sSourceFile, INT dwSourceIndex)
 
 
 	if ( !hiconLarge ||  !hiconSmall)
-	{ WARN("failure loading icon %i from %s (%x %x)\n", dwSourceIndex, sSourceFile, hiconLarge, hiconSmall);
+	{
+	  WARN("failure loading icon %i from %s (%x %x)\n", dwSourceIndex, sSourceFile, hiconLarge, hiconSmall);
 	  return -1;
 	}
 	return SIC_IconAppend (sSourceFile, dwSourceIndex, hiconSmall, hiconLarge);		
@@ -541,23 +552,32 @@ static INT SIC_LoadIcon (LPCSTR sSourceFile, INT dwSourceIndex)
  */
 INT SIC_GetIconIndex (LPCSTR sSourceFile, INT dwSourceIndex )
 {	SIC_ENTRY sice;
-	INT index = INVALID_INDEX;
+	INT ret, index = INVALID_INDEX;
 		
 	TRACE("%s %i\n", sSourceFile, dwSourceIndex);
 
 	sice.sSourceFile = PathFindFilenameA(sSourceFile);
 	sice.dwSourceIndex = dwSourceIndex;
 	
+	EnterCriticalSection(&SHELL32_SicCS);
+
 	if (NULL != pDPA_GetPtr (sic_hdpa, 0))
-	{ index = pDPA_Search (sic_hdpa, &sice, -1L, SIC_CompareEntrys, 0, 0);
+	{
+	  index = pDPA_Search (sic_hdpa, &sice, -1L, SIC_CompareEntrys, 0, 0);
 	}
 
 	if ( INVALID_INDEX == index )
-	{  return SIC_LoadIcon (sSourceFile, dwSourceIndex);
+	{
+	  ret = SIC_LoadIcon (sSourceFile, dwSourceIndex);
 	}
-	
-	TRACE("-- found\n");
-	return ((LPSIC_ENTRY)pDPA_GetPtr(sic_hdpa, index))->dwListIndex;
+	else
+	{
+	  TRACE("-- found\n");
+	  ret = ((LPSIC_ENTRY)pDPA_GetPtr(sic_hdpa, index))->dwListIndex;
+	}
+
+	LeaveCriticalSection(&SHELL32_SicCS);
+	return ret;
 }
 /****************************************************************************
  * SIC_LoadIcon				[internal]
@@ -571,8 +591,10 @@ static HICON WINE_UNUSED SIC_GetIcon (LPCSTR sSourceFile, INT dwSourceIndex, BOO
 	TRACE("%s %i\n", sSourceFile, dwSourceIndex);
 
 	index = SIC_GetIconIndex(sSourceFile, dwSourceIndex);
+
 	if (INVALID_INDEX == index)
-	{ return INVALID_INDEX;
+	{
+	  return INVALID_INDEX;
 	}
 
 	if (bSmallIcon)
@@ -588,9 +610,8 @@ static HICON WINE_UNUSED SIC_GetIcon (LPCSTR sSourceFile, INT dwSourceIndex, BOO
  *  will be removed when the resource-compiler is ready
  */
 BOOL SIC_Initialize(void)
-{	CHAR   		szShellPath[MAX_PATH];
-	HGLOBAL	hSmRet, hLgRet;
-	HICON		*pSmRet, *pLgRet;
+{
+	HICON		hSm, hLg;
 	UINT		index;
 
 	TRACE("\n");
@@ -598,45 +619,33 @@ BOOL SIC_Initialize(void)
 	if (sic_hdpa)	/* already initialized?*/
 	  return TRUE;
 	  
-	sic_hdpa = pDPA_Create(16);
+	InitializeCriticalSection(&SHELL32_SicCS);
 
+	sic_hdpa = pDPA_Create(16);
+	
 	if (!sic_hdpa)
-	{ return(FALSE);
+	{
+	  return(FALSE);
 	}
 
-	GetSystemDirectoryA(szShellPath,MAX_PATH);
-	PathAddBackslashA(szShellPath);
-	strcat(szShellPath,"shell32.dll");
-
-	hSmRet = GlobalAlloc( GMEM_FIXED | GMEM_ZEROINIT, sizeof(HICON)*40);
-	hLgRet = GlobalAlloc( GMEM_FIXED | GMEM_ZEROINIT, sizeof(HICON)*40);
-
-	pSmRet = (HICON*)GlobalLock(hSmRet);
-	pLgRet = (HICON*)GlobalLock(hLgRet);
-
-	ExtractIconExA ( szShellPath, 0, pLgRet, pSmRet, 40 );
-
 	ShellSmallIconList = pImageList_Create(16,16,ILC_COLORDDB | ILC_MASK,0,0x20);
 	ShellBigIconList = pImageList_Create(32,32,ILC_COLORDDB | ILC_MASK,0,0x20);
 
 	pImageList_SetBkColor(ShellSmallIconList, GetSysColor(COLOR_WINDOW));
 	pImageList_SetBkColor(ShellBigIconList, GetSysColor(COLOR_WINDOW));
 
-	for (index=0; index<40; index++)
-	{ if (! pSmRet[index] )
-	  { MESSAGE("*** failure loading resources from %s\n", szShellPath );
-	    MESSAGE("*** this is a hack for loading the internal and external dll at the same time\n");
-	    MESSAGE("*** you can ignore it but you will miss some icons in win95 dialogs\n\n");
-	    break;
+	for (index=1; index<39; index++)
+	{
+	  hSm = LoadImageA(shell32_hInstance, MAKEINTRESOURCEA(index), IMAGE_ICON, 16, 16,LR_SHARED);
+	  hLg = LoadImageA(shell32_hInstance, MAKEINTRESOURCEA(index), IMAGE_ICON, 32, 32,LR_SHARED);
+
+	  if(!hSm)
+	  {
+	    hSm = LoadImageA(shell32_hInstance, MAKEINTRESOURCEA(0), IMAGE_ICON, 16, 16,LR_SHARED);
+	    hLg = LoadImageA(shell32_hInstance, MAKEINTRESOURCEA(0), IMAGE_ICON, 32, 32,LR_SHARED);
 	  }
-	  SIC_IconAppend (szShellPath, index, pSmRet[index], pLgRet[index]);
+	  SIC_IconAppend ("shell32.dll", index, hSm, hLg);
 	}
-		
-	GlobalUnlock(hLgRet);
-	GlobalFree(hLgRet);
-
-	GlobalUnlock(hSmRet);
-	GlobalFree(hSmRet);
 
 	TRACE("hIconSmall=%p hIconBig=%p\n",ShellSmallIconList, ShellBigIconList);
 
@@ -654,6 +663,8 @@ void SIC_Destroy(void)
 
 	TRACE("\n");
 
+	EnterCriticalSection(&SHELL32_SicCS);
+
 	if (sic_hdpa && NULL != pDPA_GetPtr (sic_hdpa, 0))
 	{
 	  for (i=0; i < pDPA_GetPtrCount(sic_hdpa); ++i)
@@ -665,6 +676,8 @@ void SIC_Destroy(void)
 	}
 
 	sic_hdpa = NULL;
+
+	LeaveCriticalSection(&SHELL32_SicCS);
 }
 /*************************************************************************
  * Shell_GetImageList			[SHELL32.71]
@@ -733,7 +746,7 @@ UINT WINAPI SHMapPIDLToSystemImageListIndex(LPSHELLFOLDER sh, LPITEMIDLIST pidl,
 {
 	UINT	Index;
 
-	WARN("(SF=%p,pidl=%p,%p)\n",sh,pidl,pIndex);
+	TRACE("(SF=%p,pidl=%p,%p)\n",sh,pidl,pIndex);
 	pdump(pidl);
 	
 	if (pIndex)
-- 
GitLab