shell32 patch 12 - fix bounds checking
Mike McCormack
mike at codeweavers.com
Sun Feb 8 04:10:16 CST 2004
ChangeLog:
* fix the bounds checking in SHGetPathFromIDListA/W
Mike
Mike McCormack wrote:
>
> This patch broke the installation of IE6.
>
> When running the command below during installation of IE6, a pathname is
> scribbled over the stack...
>
> C:\windows\inf\unregmp2.exe /Shortcuts /IE5 /RegExts
>
> Any ideas why?
>
> Mike
-------------- next part --------------
Index: dlls/shell32/pidl.c
===================================================================
RCS file: /home/wine/wine/dlls/shell32/pidl.c,v
retrieving revision 1.101
diff -u -r1.101 pidl.c
--- dlls/shell32/pidl.c 27 Jan 2004 00:01:43 -0000 1.101
+++ dlls/shell32/pidl.c 8 Feb 2004 00:07:32 -0000
@@ -1284,16 +1284,16 @@
*/
HRESULT SHELL_GetPathFromIDListA(LPCITEMIDLIST pidl, LPSTR pszPath, UINT uOutSize)
{
- LPSTR pstr = pszPath;
- LPSTR end = pszPath + uOutSize;
HRESULT hr = S_OK;
+ pszPath[0]=0;
+
/* One case is a PIDL rooted at desktop level */
if (_ILIsValue(pidl) || _ILIsFolder(pidl)) {
- hr = SHGetSpecialFolderPathA(0, pstr, CSIDL_DESKTOP, FALSE);
+ hr = SHGetSpecialFolderPathA(0, pszPath, CSIDL_DESKTOP, FALSE);
if (SUCCEEDED(hr))
- pstr = PathAddBackslashA(pstr);
+ PathAddBackslashA(pszPath);
}
/* The only other valid case is a item ID list beginning at "My Computer" */
else if (_ILIsMyComputer(pidl))
@@ -1302,7 +1302,7 @@
if (SUCCEEDED(hr)) {
LPSTR txt;
- while(pidl && pidl->mkid.cb && pstr<end) {
+ while(pidl && pidl->mkid.cb) {
if (_ILIsSpecialFolder(pidl))
{hr = E_INVALIDARG; break;}
@@ -1310,7 +1310,13 @@
if (!txt)
{hr = E_INVALIDARG; break;}
- lstrcpynA(pstr, txt, end-pstr);
+ if (lstrlenA(txt) > pidl->mkid.cb)
+ ERR("pidl %p is borked\n",pidl);
+
+ /* make sure there's enough space for the next segment */
+ if ( (lstrlenA(txt) + lstrlenA(pszPath)) > uOutSize)
+ {hr = E_INVALIDARG; break;}
+ lstrcatA( pszPath, txt );
pidl = ILGetNext(pidl);
if (!pidl)
@@ -1321,8 +1327,9 @@
break;
}
- pstr = PathAddBackslashA(pstr);
- if (!pstr)
+ if( (lstrlenA(pszPath) + 1) > uOutSize)
+ {hr = E_INVALIDARG; break;}
+ if (!PathAddBackslashA(pszPath))
{hr = E_INVALIDARG; break;}
}
} else
@@ -1367,16 +1374,17 @@
*/
HRESULT SHELL_GetPathFromIDListW(LPCITEMIDLIST pidl, LPWSTR pszPath, UINT uOutSize)
{
- LPWSTR pstr = pszPath;
- LPWSTR end = pszPath + uOutSize;
HRESULT hr = S_OK;
+ UINT len;
+
+ pszPath[0]=0;
/* One case is a PIDL rooted at desktop level */
if (_ILIsValue(pidl) || _ILIsFolder(pidl)) {
- hr = SHGetSpecialFolderPathW(0, pstr, CSIDL_DESKTOP, FALSE);
+ hr = SHGetSpecialFolderPathW(0, pszPath, CSIDL_DESKTOP, FALSE);
if (SUCCEEDED(hr))
- pstr = PathAddBackslashW(pstr);
+ PathAddBackslashW(pszPath);
}
/* The only other valid case is a item ID list beginning at "My Computer" */
else if (_ILIsMyComputer(pidl))
@@ -1385,7 +1393,7 @@
if (SUCCEEDED(hr)) {
LPSTR txt;
- while(pidl && pidl->mkid.cb && pstr<end) {
+ while(pidl && pidl->mkid.cb) {
if (_ILIsSpecialFolder(pidl))
{hr = E_INVALIDARG; break;}
@@ -1393,8 +1401,14 @@
if (!txt)
{hr = E_INVALIDARG; break;}
- if (!MultiByteToWideChar(CP_ACP, 0, txt, -1, pstr, uOutSize))
- {hr = E_OUTOFMEMORY; break;}
+ if (lstrlenA(txt) > pidl->mkid.cb)
+ ERR("pidl %p is borked\n",pidl);
+ len = MultiByteToWideChar(CP_ACP, 0, txt, -1, NULL, 0);
+ if ( (lstrlenW(pszPath) + len) > uOutSize )
+ {hr = E_INVALIDARG; break;}
+
+ MultiByteToWideChar(CP_ACP, 0, txt, -1,
+ &pszPath[lstrlenW(pszPath)], len);
pidl = ILGetNext(pidl);
if (!pidl)
@@ -1405,8 +1419,9 @@
break;
}
- pstr = PathAddBackslashW(pstr);
- if (!pstr)
+ if ( (lstrlenW(pszPath) + 1) > uOutSize )
+ {hr = E_INVALIDARG; break;}
+ if (!PathAddBackslashW(pszPath))
{hr = E_INVALIDARG; break;}
}
} else
More information about the wine-patches
mailing list