- made IShellFolder a aggregable object
- SHCoCreateInstance can create CSIDL_FSFolder now
- browsing into folders on the desktop implemented
- corrected returnvalue of Ico_ExtractIconEx
- fixed SHGetDataFromIDList to return data of simple pidls

diff --git a/dlls/shell32/classes.c b/dlls/shell32/classes.c
index b656b5c..349a569 100644
--- a/dlls/shell32/classes.c
+++ b/dlls/shell32/classes.c
@@ -136,7 +136,7 @@
 	    LoadStringA(shell32_hInstance, IDS_DESKTOP, szDest, buflen);
 	    ret = TRUE;
 	  }
-	  else if (IsEqualIID(riid, &IID_MyComputer))
+	  else if (IsEqualIID(riid, &CLSID_MyComputer))
 	  {
 	    LoadStringA(shell32_hInstance, IDS_MYCOMPUTER, szDest, buflen);
 	    ret = TRUE;
@@ -152,6 +152,9 @@
 *	HCR_GetFolderAttributes	[internal]
 *
 * gets the folder attributes of a class
+*
+* FIXME
+*	verify the defaultvalue for *szDest
 */
 BOOL HCR_GetFolderAttributes (REFIID riid, LPDWORD szDest)
 {	HKEY	hkey;
@@ -163,6 +166,9 @@
 	WINE_StringFromCLSID(riid,&xriid[strlen(xriid)]);
 	TRACE("%s\n",xriid );
 
+	if (!szDest) return FALSE;
+	*szDest = SFGAO_FOLDER|SFGAO_FILESYSTEM;
+	
 	strcat (xriid, "\\ShellFolder");
 
 	if (RegOpenKeyExA(HKEY_CLASSES_ROOT,xriid,0,KEY_READ,&hkey))
diff --git a/dlls/shell32/iconcache.c b/dlls/shell32/iconcache.c
index 14bd6b0..1c34ee5 100644
--- a/dlls/shell32/iconcache.c
+++ b/dlls/shell32/iconcache.c
@@ -203,18 +203,12 @@
 }
 
 /*************************************************************************
- *			InternalExtractIcon		[SHELL.39]
  *
- * This abortion is called directly by Progman
- *  fixme: the icon section is broken (don't have a handle for
- *    ICO_GetIconDirectory....)
- *
+ * returns
+ *  failure:0; success: icon handle or nr of icons (nIconIndex-1)
  */
-#define ICO_INVALID_FILE	1
-#define ICO_NO_ICONS		0
-
-HGLOBAL WINAPI ICO_ExtractIconEx(LPCSTR lpszExeFileName, HICON * RetPtr, UINT nIconIndex, UINT n, UINT cxDesired, UINT cyDesired )
-{	HGLOBAL	hRet = ICO_NO_ICONS;
+HICON WINAPI ICO_ExtractIconEx(LPCSTR lpszExeFileName, HICON * RetPtr, UINT nIconIndex, UINT n, UINT cxDesired, UINT cyDesired )
+{	HGLOBAL		hRet = 0;
 	LPBYTE		pData;
 	OFSTRUCT	ofs;
 	DWORD		sig;
@@ -227,7 +221,7 @@
 	TRACE("(file %s,start %d,extract %d\n", lpszExeFileName, nIconIndex, n);
 
 	if( hFile == HFILE_ERROR || !n )
-	  return ICO_INVALID_FILE;
+	  return hRet;
 
 	sig = SHELL_GetResourceTable(hFile,&pData);
 
@@ -321,13 +315,11 @@
 		  
 	  if ( !(fmapping = CreateFileMappingA(hFile,NULL,PAGE_READONLY|SEC_COMMIT,0,0,NULL))) 
 	  { WARN("failed to create filemap.\n");	/* FIXME, INVALID_HANDLE_VALUE? */
-	    hRet = ICO_INVALID_FILE;
 	    goto end_2;		/* failure */
 	  }
 
 	  if ( !(peimage = MapViewOfFile(fmapping,FILE_MAP_READ,0,0,0))) 
 	  { WARN("failed to mmap filemap.\n");
-	    hRet = ICO_INVALID_FILE;
 	    goto end_2;		/* failure */
 	  }
 
@@ -348,12 +340,12 @@
 
 	  if (!rootresdir) 
 	  { WARN("haven't found section for resource directory.\n");
-	    goto end_4;		/* failure */
+	    goto end_3;		/* failure */
 	  }
   /* search the group icon dir*/
 	  if (!(icongroupresdir = GetResDirEntryW(rootresdir,RT_GROUP_ICONW, (DWORD)rootresdir,FALSE))) 
 	  { WARN("No Icongroupresourcedirectory!\n");
-	    goto end_4;		/* failure */
+	    goto end_3;		/* failure */
 	  }
 	  iconDirCount = icongroupresdir->NumberOfNamedEntries+icongroupresdir->NumberOfIdEntries;
 
@@ -365,7 +357,7 @@
 
 	  if (nIconIndex >= iconDirCount) 
 	  { WARN("nIconIndex %d is larger than iconDirCount %d\n",nIconIndex,iconDirCount);
-	    goto end_4;		/* failure */
+	    goto end_3;		/* failure */
 	  }
 
 	  xresent = (PIMAGE_RESOURCE_DIRECTORY_ENTRY)(icongroupresdir+1);	/* caller just wanted the number of entries */
@@ -399,14 +391,14 @@
 
 	    if (!igdata) 
 	    { WARN("no matching real address for icongroup!\n");
-	      goto end_4;	/* failure */
+	      goto end_3;	/* failure */
 	    }
 	    RetPtr[i] = (HICON)pLookupIconIdFromDirectoryEx(igdata, TRUE, cxDesired, cyDesired, LR_DEFAULTCOLOR);
 	  }
 
 	  if (!(iconresdir=GetResDirEntryW(rootresdir,RT_ICONW,(DWORD)rootresdir,FALSE))) 
 	  { WARN("No Iconresourcedirectory!\n");
-	    goto end_4;		/* failure */
+	    goto end_3;		/* failure */
 	  }
 
 	  for (i=0;i<n;i++) 
@@ -434,11 +426,9 @@
 	  hRet = RetPtr[0];	/* return first icon */
 	  goto end_3;		/* sucess */
 	}
-	hRet = ICO_INVALID_FILE;
 	goto end_1;		/* unknown filetype */
 
 /* cleaning up (try & catch would be nicer:-) ) */
-end_4:	hRet = 0;	/* failure */
 end_3:	UnmapViewOfFile(peimage);	/* success */
 end_2:	CloseHandle(fmapping);
 end_1:	_lclose( hFile);
diff --git a/dlls/shell32/pidl.c b/dlls/shell32/pidl.c
index 636a3fd..0505b44 100644
--- a/dlls/shell32/pidl.c
+++ b/dlls/shell32/pidl.c
@@ -12,6 +12,7 @@
 #include <stdlib.h>
 #include <string.h>
 #include <assert.h>
+#include "winbase.h"
 #include "debugtools.h"
 #include "shell.h"
 #include "shlguid.h"
@@ -55,8 +56,8 @@
 	    do
 	    {
 	      type   = _ILGetDataPointer(pidltemp)->type;
-	      szData = _ILGetTextPointer(type, _ILGetDataPointer(pidltemp));
-	      szShortName = _ILGetSTextPointer(type, _ILGetDataPointer(pidltemp));
+	      szData = _ILGetTextPointer(pidltemp);
+	      szShortName = _ILGetSTextPointer(pidltemp);
 	      _ILSimpleGetText(pidltemp, szName, MAX_PATH);
 
 	      MESSAGE ("-- pidl=%p size=%u type=%lx name=%s (%s,%s)\n",
@@ -70,6 +71,7 @@
 	  {
 	    MESSAGE ("empty pidl (Desktop)\n");
 	  }
+	  pcheck(pidl);
 	}
 
 	__SET_DEBUGGING(__DBCL_TRACE, dbch_shell, bIsShellDebug);
@@ -848,6 +850,9 @@
 /*************************************************************************
  * SHGetDataFromIDListA [SHELL32.247]
  *
+ * NOTES
+ *  the pidl can be a simple one. since we cant get the path out of the pidl
+ *  we have to take all data from the pidl
  */
 HRESULT WINAPI SHGetDataFromIDListA(LPSHELLFOLDER psf, LPCITEMIDLIST pidl, int nFormat, LPVOID dest, int len)
 {
@@ -860,18 +865,15 @@
 	  case SHGDFIL_FINDDATA:
 	    {
 	       WIN32_FIND_DATAA * pfd = dest;
-	       CHAR	pszPath[MAX_PATH];
-	       HANDLE	handle;
 
-	       if ( len < sizeof (WIN32_FIND_DATAA)) {
-		 ERR_(shell)("%d does not find sizeof(finddata)\n",len);
-	         return E_INVALIDARG;
-	       }
+	       if ( len < sizeof (WIN32_FIND_DATAA)) return E_INVALIDARG;
 
-	       SHGetPathFromIDListA(pidl, pszPath);
-
-	       if ((handle  = FindFirstFileA ( pszPath, pfd)))
-	         FindClose (handle);
+	       ZeroMemory(pfd, sizeof (WIN32_FIND_DATAA));
+	       _ILGetFileDateTime( pidl, &(pfd->ftLastWriteTime));
+	       pfd->dwFileAttributes = _ILGetFileAttributes(pidl, NULL, 0);
+	       pfd->nFileSizeLow = _ILGetFileSize ( pidl, NULL, 0);
+	       lstrcpynA(pfd->cFileName,_ILGetTextPointer(pidl), MAX_PATH);
+	       lstrcpynA(pfd->cAlternateFileName,_ILGetSTextPointer(pidl), 14);
 	    }
 	    return NOERROR;
 
@@ -899,23 +901,27 @@
 	  case SHGDFIL_FINDDATA:
 	    {
 	       WIN32_FIND_DATAW * pfd = dest;
-	       WCHAR	pszPath[MAX_PATH];
-	       HANDLE	handle;
 
-	       if ( len < sizeof (WIN32_FIND_DATAW)) {
-		 ERR_(shell)("%d does not find sizeof(finddata)\n",len);
-	         return E_INVALIDARG;
-	       }
-	       SHGetPathFromIDListW(pidl, pszPath);
-	       if ((handle  = FindFirstFileW ( pszPath, pfd)))
-	         FindClose (handle);
+	       if ( len < sizeof (WIN32_FIND_DATAW)) return E_INVALIDARG;
+
+	       ZeroMemory(pfd, sizeof (WIN32_FIND_DATAA));
+	       _ILGetFileDateTime( pidl, &(pfd->ftLastWriteTime));
+	       pfd->dwFileAttributes = _ILGetFileAttributes(pidl, NULL, 0);
+	       pfd->nFileSizeLow = _ILGetFileSize ( pidl, NULL, 0);
+	       lstrcpynAtoW(pfd->cFileName,_ILGetTextPointer(pidl), MAX_PATH);
+	       lstrcpynAtoW(pfd->cAlternateFileName,_ILGetSTextPointer(pidl), 14);
 	    }
 	    return NOERROR;
-	  default: /* fallthrough */
+	  case SHGDFIL_NETRESOURCE:
+	  case SHGDFIL_DESCRIPTIONID:
+	    FIXME_(shell)("SHGDFIL %i stub\n", nFormat);
 	    break;
+
+	  default:
+	    ERR_(shell)("Unknown SHGDFIL %i, please report\n", nFormat);
 	}
-	FIXME_(shell)("(sf=%p pidl=%p nFormat=0x%04x %p 0x%04x), unhandled.\n",psf,pidl,nFormat,dest,len);
-	return SHGetDataFromIDListA( psf, pidl, nFormat, dest, len);
+
+	return E_INVALIDARG;
 }
 
 /*************************************************************************
@@ -1018,6 +1024,7 @@
 	    ILFree (pidlChild);
 
 	  SHFree (pidlParent);
+	  if (psf) IShellFolder_Release(psf);
 	}
 
 
@@ -1058,32 +1065,32 @@
 
 LPITEMIDLIST _ILCreateMyComputer()
 {	TRACE_(pidl)("()\n");
-	return _ILCreate(PT_MYCOMP, &IID_MyComputer, sizeof(GUID));
+	return _ILCreate(PT_MYCOMP, &CLSID_MyComputer, sizeof(GUID));
 }
 
 LPITEMIDLIST _ILCreateIExplore()
 {	TRACE_(pidl)("()\n");
-	return _ILCreate(PT_MYCOMP, &IID_IExplore, sizeof(GUID));
+	return _ILCreate(PT_MYCOMP, &CLSID_Internet, sizeof(GUID));
 }
 
 LPITEMIDLIST _ILCreateControl()
 {	TRACE_(pidl)("()\n");
-	return _ILCreate(PT_SPECIAL, &IID_Control, sizeof(GUID));
+	return _ILCreate(PT_SPECIAL, &CLSID_ControlPanel, sizeof(GUID));
 }
 
 LPITEMIDLIST _ILCreatePrinter()
 {	TRACE_(pidl)("()\n");
-	return _ILCreate(PT_SPECIAL, &IID_Printer, sizeof(GUID));
+	return _ILCreate(PT_SPECIAL, &CLSID_Printers, sizeof(GUID));
 }
 
 LPITEMIDLIST _ILCreateNetwork()
 {	TRACE_(pidl)("()\n");
-	return _ILCreate(PT_MYCOMP, &IID_Network, sizeof(GUID));
+	return _ILCreate(PT_MYCOMP, &CLSID_NetworkPlaces, sizeof(GUID));
 }
 
 LPITEMIDLIST _ILCreateBitBucket()
 {	TRACE_(pidl)("()\n");
-	return _ILCreate(PT_MYCOMP, &IID_BitBucket, sizeof(GUID));
+	return _ILCreate(PT_MYCOMP, &CLSID_RecycleBin, sizeof(GUID));
 }
 
 LPITEMIDLIST _ILCreateDrive( LPCSTR lpszNew)
@@ -1224,7 +1231,7 @@
 	    pidlOut->mkid.cb = uSize;
 	    pData =_ILGetDataPointer(pidlOut);
 	    pData->type = type;
-	    pszDest =  _ILGetTextPointer(type, pData);
+	    pszDest = _ILGetTextPointer(pidlOut);
 	    memcpy(pszDest, pIn, uInSize);
 	    TRACE_(pidl)("- create Drive: %s\n",debugstr_a(pszDest));
 	    break;
@@ -1237,7 +1244,7 @@
 	    pidlOut->mkid.cb = uSize;
 	    pData =_ILGetDataPointer(pidlOut);
 	    pData->type = type;
-	    pszDest =  _ILGetTextPointer(type, pData);
+	    pszDest =  _ILGetTextPointer(pidlOut);
 	    memcpy(pszDest, pIn, uInSize);
 	    TRACE_(pidl)("- create Value: %s\n",debugstr_a(pszDest));
 	    break;
@@ -1296,7 +1303,7 @@
 	TRACE_(pidl)("(%p)\n",pidl);
 
 	if (iid)
-	  return IsEqualIID(iid, &IID_MyComputer);
+	  return IsEqualIID(iid, &CLSID_MyComputer);
 	return FALSE;
 }
 
@@ -1363,7 +1370,6 @@
  */
 DWORD _ILSimpleGetText (LPCITEMIDLIST pidl, LPSTR szOut, UINT uOutSize)
 {
-	LPPIDLDATA	pData;
 	DWORD		dwReturn=0; 
 	LPSTR		szSrc;
 	GUID const * 	riid;
@@ -1376,9 +1382,7 @@
 	if (szOut)
 	  *szOut = 0;
 
-	pData = _ILGetDataPointer(pidl);
-
-	if (!pData)					
+	if (_ILIsDesktop(pidl))					
 	{
 	 /* desktop */
 	  if (HCR_GetClassName(&CLSID_ShellDesktop, szTemp, MAX_PATH))
@@ -1389,7 +1393,7 @@
 	    dwReturn = strlen (szTemp);
 	  }
 	}
-	else if (( szSrc = _ILGetTextPointer(pData->type, pData) ))
+	else if (( szSrc = _ILGetTextPointer(pidl) ))
 	{
 	  /* filesystem */
 	  if (szOut)
@@ -1435,36 +1439,37 @@
  *  _ILGetTextPointer()
  * gets a pointer to the long filename string stored in the pidl
  */
-LPSTR _ILGetTextPointer(PIDLTYPE type, LPPIDLDATA pidldata)
-{/*	TRACE(pidl,"(type=%x data=%p)\n", type, pidldata);*/
+LPSTR _ILGetTextPointer(LPCITEMIDLIST pidl)
+{/*	TRACE(pidl,"(pidl%p)\n", pidl);*/
 
-	if(!pidldata)
-	{ return NULL;
-	}
+	LPPIDLDATA pdata =_ILGetDataPointer(pidl);
 
-	switch (type)
+	if (pdata)
 	{
-	  case PT_MYCOMP:
-	  case PT_SPECIAL:
-	    return NULL;
+	  switch (pdata->type)
+	  {
+	    case PT_MYCOMP:
+	    case PT_SPECIAL:
+	      return NULL;
 
-	  case PT_DRIVE:
-	  case PT_DRIVE1:
-	  case PT_DRIVE2:
-	  case PT_DRIVE3:
-	    return (LPSTR)&(pidldata->u.drive.szDriveName);
+	    case PT_DRIVE:
+	    case PT_DRIVE1:
+	    case PT_DRIVE2:
+	    case PT_DRIVE3:
+	      return (LPSTR)&(pdata->u.drive.szDriveName);
 
-	  case PT_FOLDER:
-	  case PT_FOLDER1:
-	  case PT_VALUE:
-	  case PT_IESPECIAL:
-	    return (LPSTR)&(pidldata->u.file.szNames);
+	    case PT_FOLDER:
+	    case PT_FOLDER1:
+	    case PT_VALUE:
+	    case PT_IESPECIAL:
+	      return (LPSTR)&(pdata->u.file.szNames);
 
-	  case PT_WORKGRP:
-	  case PT_COMP:
-	  case PT_NETWORK:
-	  case PT_SHARE:
-	    return (LPSTR)&(pidldata->u.network.szNames);
+	    case PT_WORKGRP:
+	    case PT_COMP:
+	    case PT_NETWORK:
+	    case PT_SHARE:
+	      return (LPSTR)&(pdata->u.network.szNames);
+	  }
 	}
 	return NULL;
 }
@@ -1473,21 +1478,23 @@
  *  _ILGetSTextPointer()
  * gets a pointer to the short filename string stored in the pidl
  */
-LPSTR _ILGetSTextPointer(PIDLTYPE type, LPPIDLDATA pidldata)
-{/*	TRACE(pidl,"(type=%x data=%p)\n", type, pidldata);*/
+LPSTR _ILGetSTextPointer(LPCITEMIDLIST pidl)
+{/*	TRACE(pidl,"(pidl%p)\n", pidl);*/
 
-	if(!pidldata)
-	  return NULL;
+	LPPIDLDATA pdata =_ILGetDataPointer(pidl);
 
-	switch (type)
+	if (pdata)
 	{
-	  case PT_FOLDER:
-	  case PT_VALUE:
-	  case PT_IESPECIAL:
-	    return (LPSTR)(pidldata->u.file.szNames + strlen (pidldata->u.file.szNames) + 1);
+	  switch (pdata->type)
+	  {
+	    case PT_FOLDER:
+	    case PT_VALUE:
+	    case PT_IESPECIAL:
+	      return (LPSTR)(pdata->u.file.szNames + strlen (pdata->u.file.szNames) + 1);
 
-	  case PT_WORKGRP:
-	    return (LPSTR)(pidldata->u.network.szNames + strlen (pidldata->u.network.szNames) + 1);
+	    case PT_WORKGRP:
+	      return (LPSTR)(pdata->u.network.szNames + strlen (pdata->u.network.szNames) + 1);
+	  }
 	}
 	return NULL;
 }
@@ -1658,7 +1665,7 @@
 }
 
 /*************************************************************************
- * _ILGetAttributeStr
+ * _ILGetFileAttributes
  *
  * Given the ItemIdList, get the Attrib string format
  *
@@ -1668,55 +1675,52 @@
  *      uOutsize    [I] The size of the Buffer
  *
  * RETURNS
- *     True if successful
+ *     Attributes
  *
  * NOTES
  *     
  */
-BOOL _ILGetAttributeStr(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize)
+DWORD _ILGetFileAttributes(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize)
 {
-    LPPIDLDATA pData =_ILGetDataPointer(pidl);
-    WORD wAttrib;
-    int i;
+	LPPIDLDATA pData =_ILGetDataPointer(pidl);
+	WORD wAttrib = 0;
+	int i;
 
-    /* Need At Least 6 characters to represent the Attrib String */
-    if(uOutSize < 6) 
-    {
-        return FALSE;
-    }
-    switch(pData->type)
-    {
-        case PT_FOLDER:
-            wAttrib = pData->u.folder.uFileAttribs;
-            break;
-        case PT_VALUE:
-            wAttrib = pData->u.file.uFileAttribs;
-            break;
-        default:
-            return FALSE;
-    }
-    i=0;
-    if(wAttrib & FILE_ATTRIBUTE_READONLY)
-    {
-        pOut[i++] = 'R';
-    }
-    if(wAttrib & FILE_ATTRIBUTE_HIDDEN)
-    {
-        pOut[i++] = 'H';
-    }
-    if(wAttrib & FILE_ATTRIBUTE_SYSTEM)
-    {
-        pOut[i++] = 'S';
-    }
-    if(wAttrib & FILE_ATTRIBUTE_ARCHIVE)
-    {
-        pOut[i++] = 'A';
-    }
-    if(wAttrib & FILE_ATTRIBUTE_COMPRESSED)
-    {
-        pOut[i++] = 'C';
-    }
-    pOut[i] = 0x00;
-    return TRUE;
+	switch(pData->type)
+	{
+	  case PT_FOLDER:
+	    wAttrib = pData->u.folder.uFileAttribs;
+	    break;
+	  case PT_VALUE:
+	    wAttrib = pData->u.file.uFileAttribs;
+	    break;
+	}
+	
+	if(uOutSize >= 6)
+	{
+	  i=0;
+	  if(wAttrib & FILE_ATTRIBUTE_READONLY)
+	  {
+	    pOut[i++] = 'R';
+	  }
+	  if(wAttrib & FILE_ATTRIBUTE_HIDDEN)
+	  {
+	    pOut[i++] = 'H';
+	  }
+	  if(wAttrib & FILE_ATTRIBUTE_SYSTEM)
+	  {
+	    pOut[i++] = 'S';
+	  }
+	  if(wAttrib & FILE_ATTRIBUTE_ARCHIVE)
+	  {
+	    pOut[i++] = 'A';
+	  }
+	  if(wAttrib & FILE_ATTRIBUTE_COMPRESSED)
+	  {
+	    pOut[i++] = 'C';
+	  }
+	  pOut[i] = 0x00;
+	}
+	return wAttrib;
 }
 
diff --git a/dlls/shell32/pidl.h b/dlls/shell32/pidl.h
index d7d5550..cb32cb0 100644
--- a/dlls/shell32/pidl.h
+++ b/dlls/shell32/pidl.h
@@ -121,7 +121,7 @@
 DWORD	_ILGetFileSize		(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize);
 BOOL	_ILGetExtension		(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize);
 void	_ILGetFileType		(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize);
-BOOL	_ILGetAttributeStr	(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize);
+DWORD	_ILGetFileAttributes	(LPCITEMIDLIST pidl, LPSTR pOut, UINT uOutSize);
 
 BOOL	_ILGetFileDateTime	(LPCITEMIDLIST pidl, FILETIME *ft);
 DWORD	_ILGetDrive		(LPCITEMIDLIST, LPSTR, UINT16);
@@ -158,8 +158,8 @@
  * helper functions (getting struct-pointer)
  */
 LPPIDLDATA	_ILGetDataPointer	(LPCITEMIDLIST);
-LPSTR		_ILGetTextPointer	(PIDLTYPE type, LPPIDLDATA pidldata);
-LPSTR		_ILGetSTextPointer	(PIDLTYPE type, LPPIDLDATA pidldata);
+LPSTR		_ILGetTextPointer	(LPCITEMIDLIST);
+LPSTR		_ILGetSTextPointer	(LPCITEMIDLIST);
 REFIID		_ILGetGUIDPointer	(LPCITEMIDLIST pidl);
 
 /* 
diff --git a/dlls/shell32/shellole.c b/dlls/shell32/shellole.c
index 0bff960..9c37e92 100644
--- a/dlls/shell32/shellole.c
+++ b/dlls/shell32/shellole.c
@@ -28,6 +28,13 @@
 DEFAULT_DEBUG_CHANNEL(shell)
 
 DWORD WINAPI SHCLSIDFromStringA (LPSTR clsid, CLSID *id);
+extern IShellFolder * IShellFolder_Constructor(
+	IShellFolder * psf,
+	LPITEMIDLIST pidl);
+extern HRESULT IFSFolder_Constructor(
+	IUnknown * pUnkOuter,
+	REFIID riid,
+	LPVOID * ppv);
 
 /*************************************************************************
  * SHCoCreateInstance [SHELL32.102]
@@ -62,14 +69,22 @@
 	TRACE("(%p,\n\tCLSID:\t%s, unk:%p\n\tIID:\t%s,%p)\n",
 		aclsid,xclsid,unknownouter,xiid,ppv);
 
-	hres = CoCreateInstance(myclsid, unknownouter, CLSCTX_INPROC_SERVER, refiid, ppv);
-
+	if IsEqualCLSID(myclsid, &CLSID_ShellFSFolder)
+	{
+	  hres = IFSFolder_Constructor(unknownouter, refiid, ppv);
+	}
+	else
+	{
+	  hres = CoCreateInstance(myclsid, unknownouter, CLSCTX_INPROC_SERVER, refiid, ppv);
+	}
+	
 	if(hres!=S_OK)
 	{
 	  ERR("failed (0x%08lx) to create \n\tCLSID:\t%s\n\tIID:\t%s\n", hres, xclsid, xiid);
-	  ERR("you might need to import the winedefault.reg\n");
+	  ERR("class not found in registry\n");
 	}
 
+	TRACE("-- instance: %p\n",*ppv);
 	return hres;
 }
 
@@ -87,11 +102,6 @@
 	
 	*ppv = NULL;
 
-	if(IsEqualCLSID(rclsid, &CLSID_PaperBin))
-	{
-	  ERR("paper bin not implemented\n");
-	  return CLASS_E_CLASSNOTAVAILABLE;
-	}
 	if(IsEqualCLSID(rclsid, &CLSID_ShellDesktop)|| 
 	   IsEqualCLSID(rclsid, &CLSID_ShellLink))
 	{
diff --git a/dlls/shell32/shellord.c b/dlls/shell32/shellord.c
index cc78dae..15ff10c 100644
--- a/dlls/shell32/shellord.c
+++ b/dlls/shell32/shellord.c
@@ -469,10 +469,10 @@
  *     free_ptr() - frees memory using IMalloc
  *     exported by ordinal
  */
-/*#define MEM_DEBUG 1*/
+#define MEM_DEBUG 0
 DWORD WINAPI SHFree(LPVOID x) 
 {
-#ifdef MEM_DEBUG
+#if MEM_DEBUG
 	WORD len = *(LPWORD)(x-2);
 
 	if ( *(LPWORD)(x+len) != 0x7384)
@@ -503,13 +503,13 @@
 {
 	LPBYTE ret;
 
-#ifdef MEM_DEBUG
+#if MEM_DEBUG
 	ret = (LPVOID) HeapAlloc(GetProcessHeap(),0,len+6);
 #else
 	ret = (LPVOID) HeapAlloc(GetProcessHeap(),0,len);
 #endif
 
-#ifdef MEM_DEBUG
+#if MEM_DEBUG
 	*(LPWORD)(ret) = 0x8271;
 	*(LPWORD)(ret+2) = (WORD)len;
 	*(LPWORD)(ret+4+len) = 0x7384;
diff --git a/dlls/shell32/shellpath.c b/dlls/shell32/shellpath.c
index fd60bca..0a5f2e0 100644
--- a/dlls/shell32/shellpath.c
+++ b/dlls/shell32/shellpath.c
@@ -777,6 +777,7 @@
 {
 	FIXME("%p(%s) %p 0x%04lx 0x%04lx stub\n",
 	lpCommand, lpCommand, v, w,x );
+	lstrcpyA(v, lpCommand);
 	return 0;
 }
 
diff --git a/dlls/shell32/shlfolder.c b/dlls/shell32/shlfolder.c
index 9752346..4c47beb 100644
--- a/dlls/shell32/shlfolder.c
+++ b/dlls/shell32/shlfolder.c
@@ -27,7 +27,18 @@
 
 DEFAULT_DEBUG_CHANNEL(shell)
 
-#define MEM_DEBUG 1
+
+/***************************************************************************
+ * debughelper: print out the return adress
+ *  helps especially to track down unbalanced AddRef/Release
+ */
+#define MEM_DEBUG 0
+
+#if MEM_DEBUG
+#define _CALL_TRACE TRACE("called from: 0x%08x\n", *( ((UINT*)&iface)-1 ));
+#else
+#define _CALL_TRACE
+#endif
 
 typedef struct
 {
@@ -197,12 +208,14 @@
 
 typedef struct 
 {
-	ICOM_VFIELD(IShellFolder2);
+	ICOM_VFIELD(IUnknown);
 	DWORD				ref;
-
+	ICOM_VTABLE(IShellFolder2)*	lpvtblShellFolder;;
 	ICOM_VTABLE(IPersistFolder)*	lpvtblPersistFolder;
 	ICOM_VTABLE(IDropTarget)*	lpvtblDropTarget;
 	
+	IUnknown			*pUnkOuter;	/* used for aggregation */
+
 	CLSID*				pclsid;
 
 	LPSTR				sMyPath;
@@ -212,19 +225,128 @@
 	BOOL		fAcceptFmt;			/* flag for pending Drop */
 } IGenericSFImpl;
 
+static struct ICOM_VTABLE(IUnknown) unkvt;
 static struct ICOM_VTABLE(IShellFolder2) sfvt;
 static struct ICOM_VTABLE(IPersistFolder) psfvt;
 static struct ICOM_VTABLE(IDropTarget) dtvt;
 
 static IShellFolder * ISF_MyComputer_Constructor(void);
 
+#define _IShellFolder2_Offset ((int)(&(((IGenericSFImpl*)0)->lpvtblShellFolder))) 
+#define _ICOM_THIS_From_IShellFolder2(class, name) class* This = (class*)(((char*)name)-_IShellFolder2_Offset); 
+	
 #define _IPersistFolder_Offset ((int)(&(((IGenericSFImpl*)0)->lpvtblPersistFolder))) 
 #define _ICOM_THIS_From_IPersistFolder(class, name) class* This = (class*)(((char*)name)-_IPersistFolder_Offset); 
 	
-static struct ICOM_VTABLE(IDropTarget) dtvt;
 #define _IDropTarget_Offset ((int)(&(((IGenericSFImpl*)0)->lpvtblDropTarget))) 
 #define _ICOM_THIS_From_IDropTarget(class, name) class* This = (class*)(((char*)name)-_IDropTarget_Offset); 
 
+/*
+  converts This to a interface pointer
+*/
+#define _IUnknown_(This)	(IUnknown*)&(This->lpVtbl)
+#define _IShellFolder_(This)	(IShellFolder*)&(This->lpvtblShellFolder)
+#define _IShellFolder2_(This)	(IShellFolder2*)&(This->lpvtblShellFolder)
+#define _IPersist_(This)	(IPersist*)&(This->lpvtblPersistFolder)
+#define _IPersistFolder_(This)	(IPersistFolder*)&(This->lpvtblPersistFolder)
+#define _IDropTarget_(This)	(IDropTarget*)&(This->lpvtblDropTarget)
+/**************************************************************************
+*	registers clipboardformat once
+*/
+static void SF_RegisterClipFmt (IGenericSFImpl * This)
+{
+	TRACE("(%p)\n", This);
+
+	if (!This->cfShellIDList)
+	{
+	  This->cfShellIDList = RegisterClipboardFormatA(CFSTR_SHELLIDLIST);
+	}
+}
+
+/**************************************************************************
+*	we need a seperate IUnknown to handle aggregation
+*	(inner IUnknown)
+*/
+static HRESULT WINAPI IUnknown_fnQueryInterface(
+	IUnknown * iface,
+	REFIID riid,
+	LPVOID *ppvObj)
+{
+	ICOM_THIS(IGenericSFImpl, iface);
+
+	char	xriid[50];	
+	WINE_StringFromCLSID((LPCLSID)riid,xriid);
+
+	_CALL_TRACE
+	TRACE("(%p)->(\n\tIID:\t%s,%p)\n",This,xriid,ppvObj);
+
+	*ppvObj = NULL;
+
+	if(IsEqualIID(riid, &IID_IUnknown))		*ppvObj = _IUnknown_(This); 
+	else if(IsEqualIID(riid, &IID_IShellFolder))	*ppvObj = _IShellFolder_(This);
+	else if(IsEqualIID(riid, &IID_IShellFolder2))	*ppvObj = _IShellFolder_(This);
+	else if(IsEqualIID(riid, &IID_IPersist))	*ppvObj = _IPersist_(This);
+	else if(IsEqualIID(riid, &IID_IPersistFolder))	*ppvObj = _IPersistFolder_(This);
+	else if(IsEqualIID(riid, &IID_IDropTarget))
+	{
+	  *ppvObj = _IDropTarget_(This);
+	  SF_RegisterClipFmt(This);
+	}
+
+	if(*ppvObj)
+	{
+	  IUnknown_AddRef((IUnknown*)(*ppvObj));
+	  TRACE("-- Interface = %p\n", *ppvObj);
+	  return S_OK;
+	}
+	TRACE("-- Interface: E_NOINTERFACE\n");
+	return E_NOINTERFACE;
+}
+
+static ULONG WINAPI IUnknown_fnAddRef(IUnknown * iface)
+{
+	ICOM_THIS(IGenericSFImpl, iface);
+
+	_CALL_TRACE
+	TRACE("(%p)->(count=%lu)\n",This,This->ref);
+
+	shell32_ObjCount++;
+	return ++(This->ref);
+}
+
+static ULONG WINAPI IUnknown_fnRelease(IUnknown * iface) 
+{
+	ICOM_THIS(IGenericSFImpl, iface);
+
+	_CALL_TRACE
+	TRACE("(%p)->(count=%lu)\n",This,This->ref);
+
+	shell32_ObjCount--;
+	if (!--(This->ref)) 
+	{
+	  TRACE("-- destroying IShellFolder(%p)\n",This);
+
+	  if (pdesktopfolder == _IShellFolder_(This))
+	  {
+	    pdesktopfolder=NULL;
+	    TRACE("-- destroyed IShellFolder(%p) was Desktopfolder\n",This);
+	  }
+	  if(This->absPidl) SHFree(This->absPidl);
+	  if(This->sMyPath) SHFree(This->sMyPath);
+	  HeapFree(GetProcessHeap(),0,This);
+	  return 0;
+	}
+	return This->ref;
+}
+
+static ICOM_VTABLE(IUnknown) unkvt = 
+{	
+	ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
+	IUnknown_fnQueryInterface,
+	IUnknown_fnAddRef,
+	IUnknown_fnRelease,
+};
+
 static shvheader GenericSFHeader [] =
 {
  { IDS_SHV_COLUMN1, SHCOLSTATE_TYPE_STR | SHCOLSTATE_ONBYDEFAULT, LVCFMT_RIGHT, 15 },
@@ -236,58 +358,95 @@
 #define GENERICSHELLVIEWCOLUMNS 5
 
 /**************************************************************************
-*	registers clipboardformat once
+*	IShellFolder_Constructor
+*
+* NOTES
+*  creating undocumented ShellFS_Folder as part of an aggregation
+*  {F3364BA0-65B9-11CE-A9BA-00AA004AE837}
+*
+* FIXME
+*	when pUnkOuter = 0 then rrid = IID_IShellFolder is returned
 */
-static void SF_RegisterClipFmt (IShellFolder2 * iface)
+HRESULT IFSFolder_Constructor(
+	IUnknown * pUnkOuter,
+	REFIID riid,
+	LPVOID * ppv)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	IGenericSFImpl *	sf;
+	char	xriid[50];	
+	HRESULT hr = S_OK;
+	WINE_StringFromCLSID((LPCLSID)riid,xriid);
 
-	TRACE("(%p)\n", This);
+	TRACE("unkOut=%p riid=%s\n",pUnkOuter, xriid);
 
-	if (!This->cfShellIDList)
+	if(pUnkOuter && ! IsEqualIID(riid, &IID_IUnknown))
 	{
-	  This->cfShellIDList = RegisterClipboardFormatA(CFSTR_SHELLIDLIST);
+	  hr = CLASS_E_NOAGGREGATION;	/* forbidden by definition */
 	}
+	else
+	{
+	  sf=(IGenericSFImpl*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IGenericSFImpl));
+	  if (sf)
+	  {
+	    sf->ref=1;
+	    ICOM_VTBL(sf)=&unkvt;
+	    sf->lpvtblShellFolder=&sfvt;
+	    sf->lpvtblPersistFolder=&psfvt;
+	    sf->lpvtblDropTarget=&dtvt;
+	    sf->pclsid = (CLSID*)&CLSID_SFFile;
+	    sf->pUnkOuter = pUnkOuter ? pUnkOuter : _IUnknown_(sf);
+	    *ppv = _IUnknown_(sf);
+	    hr = S_OK;
+	    shell32_ObjCount++;
+	  }
+	  else
+	  {
+	    hr = E_OUTOFMEMORY;
+	  }
+	}
+	return hr;
 }
-
 /**************************************************************************
 *	  IShellFolder_Constructor
 *
+* NOTES
+*	THIS points to the parent folder
 */
 
-static IShellFolder * IShellFolder_Constructor(
-	IShellFolder * psf,
+IShellFolder * IShellFolder_Constructor(
+	IShellFolder2 * iface,
 	LPITEMIDLIST pidl)
 {
 	IGenericSFImpl *	sf;
-	IGenericSFImpl * 	sfParent = (IGenericSFImpl*) psf;
 	DWORD			dwSize=0;
 
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
+
 	sf=(IGenericSFImpl*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IGenericSFImpl));
 	sf->ref=1;
 
-	ICOM_VTBL(sf)=&sfvt;
+	ICOM_VTBL(sf)=&unkvt;
+	sf->lpvtblShellFolder=&sfvt;
 	sf->lpvtblPersistFolder=&psfvt;
 	sf->lpvtblDropTarget=&dtvt;
 	sf->pclsid = (CLSID*)&CLSID_SFFile;
-	sf->cfShellIDList=0;
-	sf->fAcceptFmt=FALSE;
+	sf->pUnkOuter = _IUnknown_(sf);
 
-	TRACE("(%p)->(parent=%p, pidl=%p)\n",sf,sfParent, pidl);
+	TRACE("(%p)->(parent=%p, pidl=%p)\n",sf,This, pidl);
 	pdump(pidl);
 		
-	if(pidl)						/* do we have a pidl? */
+	if(pidl && iface)				/* do we have a pidl? */
 	{
 	  int len;
 
-	  sf->absPidl = ILCombine(sfParent->absPidl, pidl);	/* build a absolute pidl */
+	  sf->absPidl = ILCombine(This->absPidl, pidl);	/* build a absolute pidl */
 
 	  if (!_ILIsSpecialFolder(pidl))				/* only file system paths */
 	  {
-	    if(sfParent->sMyPath)				/* get the size of the parents path */
+	    if(This->sMyPath)				/* get the size of the parents path */
 	    {
-	      dwSize += strlen(sfParent->sMyPath) ;
-	      TRACE("-- (%p)->(parent's path=%s)\n",sf, debugstr_a(sfParent->sMyPath));
+	      dwSize += strlen(This->sMyPath) ;
+	      TRACE("-- (%p)->(parent's path=%s)\n",sf, debugstr_a(This->sMyPath));
 	    }   
 
 	    dwSize += _ILSimpleGetText(pidl,NULL,0);		/* add the size of our name*/
@@ -296,9 +455,9 @@
 	    if(!sf->sMyPath) return NULL;
 	    *(sf->sMyPath)=0x00;
 
-	    if(sfParent->sMyPath)				/* if the parent has a path, get it*/
+	    if(This->sMyPath)				/* if the parent has a path, get it*/
 	    {
-	      strcpy(sf->sMyPath, sfParent->sMyPath);
+	      strcpy(sf->sMyPath, This->sMyPath);
 	      PathAddBackslashA (sf->sMyPath);
 	    }
 
@@ -312,8 +471,9 @@
 	}
 
 	shell32_ObjCount++;
-	return (IShellFolder *)sf;
+	return _IShellFolder_(sf);
 }
+
 /**************************************************************************
  *  IShellFolder_fnQueryInterface
  *
@@ -326,47 +486,14 @@
 	REFIID riid,
 	LPVOID *ppvObj)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	char	xriid[50];	
 	WINE_StringFromCLSID((LPCLSID)riid,xriid);
+	_CALL_TRACE
 	TRACE("(%p)->(\n\tIID:\t%s,%p)\n",This,xriid,ppvObj);
 
-	*ppvObj = NULL;
-
-	if(IsEqualIID(riid, &IID_IUnknown))
-	{ *ppvObj = This; 
-	}
-	else if(IsEqualIID(riid, &IID_IShellFolder))
-	{
-	  *ppvObj = (IShellFolder*)This;
-	}
-	else if(IsEqualIID(riid, &IID_IShellFolder2))
-	{
-	  *ppvObj = (IShellFolder2*)This;
-	}
-	else if(IsEqualIID(riid, &IID_IPersist))
-	{
-	  *ppvObj = (IPersistFolder*)&(This->lpvtblPersistFolder);
-	}
-	else if(IsEqualIID(riid, &IID_IPersistFolder))
-	{
-	  *ppvObj = (IPersistFolder*)&(This->lpvtblPersistFolder);
-	}
-	else if(IsEqualIID(riid, &IID_IDropTarget))
-	{
-	  *ppvObj = (IDropTarget*)&(This->lpvtblDropTarget);
-	  SF_RegisterClipFmt((IShellFolder2*)This);
-	}
-
-	if(*ppvObj)
-	{
-	  IUnknown_AddRef((IUnknown*)(*ppvObj));
-	  TRACE("-- Interface = %p\n", *ppvObj);
-	  return S_OK;
-	}
-	TRACE("-- Interface: E_NOINTERFACE\n");
-	return E_NOINTERFACE;
+	return IUnknown_QueryInterface(This->pUnkOuter, riid, ppvObj);
 }
 
 /**************************************************************************
@@ -375,15 +502,12 @@
 
 static ULONG WINAPI IShellFolder_fnAddRef(IShellFolder2 * iface)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
-#ifdef MEM_DEBUG
-	TRACE("called from: 0x%08x\n", *( ((UINT*)&iface)-1 ));
-#endif
+	_CALL_TRACE
 	TRACE("(%p)->(count=%lu)\n",This,This->ref);
 
-	shell32_ObjCount++;
-	return ++(This->ref);
+	return IUnknown_AddRef(This->pUnkOuter);
 }
 
 /**************************************************************************
@@ -391,34 +515,14 @@
  */
 static ULONG WINAPI IShellFolder_fnRelease(IShellFolder2 * iface) 
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
-#ifdef MEM_DEBUG
-	TRACE("called from: 0x%08x\n", *( ((UINT*)&iface)-1 ));
-#endif
+	_CALL_TRACE
 	TRACE("(%p)->(count=%lu)\n",This,This->ref);
 
-	shell32_ObjCount--;
-	if (!--(This->ref)) 
-	{ TRACE("-- destroying IShellFolder(%p)\n",This);
-
-	  if (pdesktopfolder == (IShellFolder*) iface)
-	  { pdesktopfolder=NULL;
-	    TRACE("-- destroyed IShellFolder(%p) was Desktopfolder\n",This);
-	  }
-	  if(This->absPidl)
-	  { SHFree(This->absPidl);
-	  }
-	  if(This->sMyPath)
-	  { SHFree(This->sMyPath);
-	  }
-
-	  HeapFree(GetProcessHeap(),0,This);
-
-	  return 0;
-	}
-	return This->ref;
+	return IUnknown_Release(This->pUnkOuter);
 }
+
 /**************************************************************************
 *		IShellFolder_fnParseDisplayName
 * PARAMETERS
@@ -450,7 +554,7 @@
 	LPITEMIDLIST *ppidl,
 	DWORD *pdwAttributes)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	HRESULT		hr = E_OUTOFMEMORY;
 	LPCWSTR		szNext=NULL;
@@ -485,7 +589,7 @@
 	    /* try to analyse the next element */
 	    if (szNext && *szNext)
 	    {
-	      hr = SHELL32_ParseNextElement(hwndOwner, (IShellFolder2*)This, &pidlTemp, (LPOLESTR)szNext, pchEaten, pdwAttributes);
+	      hr = SHELL32_ParseNextElement(hwndOwner, iface, &pidlTemp, (LPOLESTR)szNext, pchEaten, pdwAttributes);
 	    }
 	    else
 	    {
@@ -514,7 +618,7 @@
 	DWORD dwFlags,
 	LPENUMIDLIST* ppEnumIDList)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	TRACE("(%p)->(HWND=0x%08x flags=0x%08lx pplist=%p)\n",This,hwndOwner,dwFlags,ppEnumIDList);
 
@@ -539,7 +643,7 @@
 static HRESULT WINAPI IShellFolder_fnBindToObject( IShellFolder2 * iface, LPCITEMIDLIST pidl,
 			LPBC pbcReserved, REFIID riid, LPVOID * ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	GUID		const * iid;
 	char		xriid[50];
 	IShellFolder	*pShellFolder, *pSubFolder;
@@ -573,7 +677,7 @@
 	else
 	{
 	  LPITEMIDLIST pidltemp = ILCloneFirst(pidl);
-	  pShellFolder = IShellFolder_Constructor((IShellFolder*)This, pidltemp);
+	  pShellFolder = IShellFolder_Constructor(iface, pidltemp);
 	  ILFree(pidltemp);
 	}
 	
@@ -608,7 +712,7 @@
 	REFIID riid,
 	LPVOID *ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	char xriid[50];
 	WINE_StringFromCLSID(riid,xriid);
@@ -641,7 +745,7 @@
 	LPCITEMIDLIST pidl1,
 	LPCITEMIDLIST pidl2)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	CHAR szTemp1[MAX_PATH];
 	CHAR szTemp2[MAX_PATH];
@@ -696,7 +800,7 @@
 	        pidlTemp = ILCloneFirst(pidl1);
 	        pidl2 = ILGetNext(pidl2);
 	
-	        hr = IShellFolder_BindToObject((IShellFolder*)This, pidlTemp, NULL, &IID_IShellFolder, (LPVOID*)&psf);
+	        hr = IShellFolder_BindToObject(iface, pidlTemp, NULL, &IID_IShellFolder, (LPVOID*)&psf);
 	        if (SUCCEEDED(hr))
 	        { 
 	          nReturn = IShellFolder_CompareIDs(psf, 0, pidl1, pidl2);
@@ -724,10 +828,13 @@
 /**************************************************************************
 *	IShellFolder_fnCreateViewObject
 */
-static HRESULT WINAPI IShellFolder_fnCreateViewObject( IShellFolder2 * iface,
-		 HWND hwndOwner, REFIID riid, LPVOID *ppvOut)
+static HRESULT WINAPI IShellFolder_fnCreateViewObject(
+	IShellFolder2 * iface,
+	HWND hwndOwner,
+	REFIID riid,
+	LPVOID *ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	LPSHELLVIEW	pShellView;
 	char		xriid[50];
@@ -742,7 +849,7 @@
 
 	  if(IsEqualIID(riid, &IID_IDropTarget))
 	  {
-	    hr = IShellFolder_QueryInterface((IShellFolder*)This, &IID_IDropTarget, ppvOut);
+	    hr = IShellFolder_QueryInterface(iface, &IID_IDropTarget, ppvOut);
 	  }
 	  else if(IsEqualIID(riid, &IID_IContextMenu))
 	  {
@@ -751,7 +858,7 @@
 	  }
 	  else if(IsEqualIID(riid, &IID_IShellView))
 	  {
-	    pShellView = IShellView_Constructor((IShellFolder *) This);
+	    pShellView = IShellView_Constructor((IShellFolder*)iface);
 	    if(pShellView)
 	    {
 	      hr = IShellView_QueryInterface(pShellView, riid, ppvOut);
@@ -772,9 +879,13 @@
 *  ULONG*          rgfInOut) //[out] result array  
 *
 */
-static HRESULT WINAPI IShellFolder_fnGetAttributesOf(IShellFolder2 * iface,UINT cidl,LPCITEMIDLIST *apidl,DWORD *rgfInOut)
+static HRESULT WINAPI IShellFolder_fnGetAttributesOf(
+	IShellFolder2 * iface,
+	UINT cidl,
+	LPCITEMIDLIST *apidl,
+	DWORD *rgfInOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	HRESULT hr = S_OK;
 
@@ -836,7 +947,7 @@
 	UINT *		prgfInOut,
 	LPVOID *	ppvOut)
 {	
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	char		xclsid[50];
 	LPITEMIDLIST	pidl;
@@ -854,7 +965,7 @@
 
 	  if(IsEqualIID(riid, &IID_IContextMenu) && (cidl >= 1))
 	  {
-	    pObj  = (LPUNKNOWN)IContextMenu_Constructor((IShellFolder *)This, This->absPidl, apidl, cidl);
+	    pObj  = (LPUNKNOWN)IContextMenu_Constructor((IShellFolder*)iface, This->absPidl, apidl, cidl);
 	    hr = S_OK;
 	  }
 	  else if (IsEqualIID(riid, &IID_IDataObject) &&(cidl >= 1))
@@ -871,7 +982,7 @@
 	  } 
 	  else if (IsEqualIID(riid, &IID_IDropTarget) && (cidl >= 1))
 	  {
-	    hr = IShellFolder_QueryInterface((IShellFolder*)This, &IID_IDropTarget, (LPVOID*)&pObj);
+	    hr = IShellFolder_QueryInterface(iface, &IID_IDropTarget, (LPVOID*)&pObj);
 	  }
 	  else
 	  { 
@@ -908,7 +1019,7 @@
 	DWORD dwFlags,
 	LPSTRRET strRet)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	CHAR		szPath[MAX_PATH]= "";
 	int		len = 0;
@@ -945,7 +1056,7 @@
 	  PathAddBackslashA(szPath);
 	  len = strlen(szPath);
 
-	  if (!SUCCEEDED(SHELL32_GetDisplayNameOfChild((IShellFolder2*)This, pidl, dwFlags, szPath + len, MAX_PATH - len)))
+	  if (!SUCCEEDED(SHELL32_GetDisplayNameOfChild(iface, pidl, dwFlags, szPath + len, MAX_PATH - len)))
 	    return E_OUTOFMEMORY;
 	}
 	strRet->uType = STRRET_CSTRA;
@@ -975,7 +1086,7 @@
 	DWORD dw, 
 	LPITEMIDLIST *pPidlOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	FIXME("(%p)->(%u,pidl=%p,%s,%lu,%p),stub!\n",
 	This,hwndOwner,pidl,debugstr_w(lpName),dw,pPidlOut);
@@ -988,7 +1099,7 @@
 */
 static HRESULT WINAPI IShellFolder_fnGetFolderPath(IShellFolder2 * iface, LPSTR lpszOut, DWORD dwOutSize)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	
 	TRACE("(%p)->(%p %lu)\n",This, lpszOut, dwOutSize);
 
@@ -1008,7 +1119,7 @@
 	IShellFolder2 * iface,
 	GUID *pguid)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1016,7 +1127,7 @@
 	IShellFolder2 * iface,
 	IEnumExtraSearch **ppenum)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1026,7 +1137,7 @@
 	ULONG *pSort,
 	ULONG *pDisplay)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	TRACE("(%p)\n",This);
 
@@ -1040,7 +1151,7 @@
 	UINT iColumn,
 	DWORD *pcsFlags)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	
 	TRACE("(%p)\n",This);
 
@@ -1056,7 +1167,7 @@
 	const SHCOLUMNID *pscid,
 	VARIANT *pv)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 
 	return E_NOTIMPL;
@@ -1067,7 +1178,7 @@
 	UINT iColumn,
 	SHELLDETAILS *psd)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	HRESULT hr = E_FAIL;
 
 	TRACE("(%p)->(%p %i %p)\n",This, pidl, iColumn, psd);
@@ -1101,7 +1212,7 @@
 	      _ILGetFileDate(pidl, psd->str.u.cStr, MAX_PATH);
 	      break;
 	    case 4:	/* attributes */
-	      _ILGetAttributeStr(pidl, psd->str.u.cStr, MAX_PATH);
+	      _ILGetFileAttributes(pidl, psd->str.u.cStr, MAX_PATH);
 	      break;
 	  }
 	  hr = S_OK;
@@ -1115,7 +1226,7 @@
 	LPCWSTR pwszName,
 	SHCOLUMNID *pscid)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1146,7 +1257,6 @@
 	IShellFolder_fnGetDetailsOf,
 	IShellFolder_fnMapNameToSCID
 };
-
 /***********************************************************************
 * 	[Desktopfolder]	IShellFolder implementation
 */
@@ -1172,13 +1282,15 @@
 
 	sf=(IGenericSFImpl*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IGenericSFImpl));
 	sf->ref=1;
-	ICOM_VTBL(sf)=&sfdvt;
+	ICOM_VTBL(sf)=&unkvt;
+	sf->lpvtblShellFolder=&sfdvt;
 	sf->absPidl=_ILCreateDesktop();	/* my qualified pidl */
+	sf->pUnkOuter = (IUnknown *) &sf->lpVtbl;
 
 	TRACE("(%p)\n",sf);
 
 	shell32_ObjCount++;
-	return (IShellFolder *)sf;
+	return _IShellFolder_(sf);
 }
 
 /**************************************************************************
@@ -1191,7 +1303,7 @@
 	REFIID riid,
 	LPVOID *ppvObj)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	char	xriid[50];	
 	WINE_StringFromCLSID((LPCLSID)riid,xriid);
@@ -1200,13 +1312,16 @@
 	*ppvObj = NULL;
 
 	if(IsEqualIID(riid, &IID_IUnknown))          /*IUnknown*/
-	{ *ppvObj = This; 
+	{
+	  *ppvObj = _IUnknown_(This); 
 	}
 	else if(IsEqualIID(riid, &IID_IShellFolder))  /*IShellFolder*/
-	{    *ppvObj = (IShellFolder*)This;
+	{
+	  *ppvObj = _IShellFolder_(This);
 	}   
 	else if(IsEqualIID(riid, &IID_IShellFolder2))  /*IShellFolder2*/
-	{    *ppvObj = (IShellFolder2*)This;
+	{
+	  *ppvObj = _IShellFolder_(This);
 	}   
 
 	if(*ppvObj)
@@ -1235,7 +1350,7 @@
 	LPITEMIDLIST *ppidl,
 	DWORD *pdwAttributes)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	LPCWSTR		szNext=NULL;
 	LPITEMIDLIST	pidlTemp=NULL;
@@ -1254,7 +1369,7 @@
 
 	if (szNext && *szNext)
 	{
-	  hr = SHELL32_ParseNextElement(hwndOwner, (IShellFolder2*)This, &pidlTemp, (LPOLESTR)szNext, pchEaten, pdwAttributes);
+	  hr = SHELL32_ParseNextElement(hwndOwner, iface, &pidlTemp, (LPOLESTR)szNext, pchEaten, pdwAttributes);
 	}
 	else
 	{
@@ -1277,7 +1392,7 @@
 	DWORD dwFlags,
 	LPENUMIDLIST* ppEnumIDList)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	TRACE("(%p)->(HWND=0x%08x flags=0x%08lx pplist=%p)\n",This,hwndOwner,dwFlags,ppEnumIDList);
 
@@ -1297,7 +1412,7 @@
 static HRESULT WINAPI ISF_Desktop_fnBindToObject( IShellFolder2 * iface, LPCITEMIDLIST pidl,
 			LPBC pbcReserved, REFIID riid, LPVOID * ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	GUID		const * clsid;
 	char		xriid[50];
 	IShellFolder	*pShellFolder, *pSubFolder;
@@ -1310,7 +1425,7 @@
 
 	if ((clsid=_ILGetGUIDPointer(pidl)))
 	{
-	  if ( IsEqualIID(clsid, &IID_MyComputer))
+	  if ( IsEqualIID(clsid, &CLSID_MyComputer))
 	  {
 	    pShellFolder = ISF_MyComputer_Constructor();
 	  }
@@ -1326,9 +1441,23 @@
 	else
 	{
 	  /* file system folder on the desktop */
-	  LPITEMIDLIST pidltemp = ILCloneFirst(pidl);
-	  pShellFolder = IShellFolder_Constructor((IShellFolder*)This, pidltemp);
-	  ILFree(pidltemp);
+	  LPITEMIDLIST deskpidl, firstpidl, completepidl;
+	  IPersistFolder * ppf;
+
+	  /* combine pidls */
+	  SHGetSpecialFolderLocation(0, CSIDL_DESKTOPDIRECTORY, &deskpidl);
+	  firstpidl = ILCloneFirst(pidl);
+	  completepidl = ILCombine(deskpidl, firstpidl);
+
+	  pShellFolder = IShellFolder_Constructor(NULL, NULL);
+	  if (SUCCEEDED(IShellFolder_QueryInterface(pShellFolder, &IID_IPersistFolder, (LPVOID*)&ppf)))
+	  {
+	    IPersistFolder_Initialize(ppf, completepidl);
+	    IPersistFolder_Release(ppf);
+	  }
+	  ILFree(completepidl);
+	  ILFree(deskpidl);
+	  ILFree(firstpidl);
 	}
 	
 	if (_ILIsPidlSimple(pidl))	/* no sub folders */
@@ -1353,7 +1482,7 @@
 static HRESULT WINAPI ISF_Desktop_fnCreateViewObject( IShellFolder2 * iface,
 		 HWND hwndOwner, REFIID riid, LPVOID *ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	LPSHELLVIEW	pShellView;
 	char		xriid[50];
@@ -1378,7 +1507,7 @@
 	  }
 	  else if(IsEqualIID(riid, &IID_IShellView))
 	  {
-	    pShellView = IShellView_Constructor((IShellFolder *) This);
+	    pShellView = IShellView_Constructor((IShellFolder*)iface);
 	    if(pShellView)
 	    {
 	      hr = IShellView_QueryInterface(pShellView, riid, ppvOut);
@@ -1395,7 +1524,7 @@
 */
 static HRESULT WINAPI ISF_Desktop_fnGetAttributesOf(IShellFolder2 * iface,UINT cidl,LPCITEMIDLIST *apidl,DWORD *rgfInOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	GUID		const * clsid;
 	DWORD		attributes;
@@ -1412,7 +1541,7 @@
 
 	  if ((clsid=_ILGetGUIDPointer(*apidl)))
 	  {
-	    if (IsEqualIID(clsid, &IID_MyComputer))
+	    if (IsEqualIID(clsid, &CLSID_MyComputer))
 	    {
 	      *rgfInOut &= 0xb0000154;
 	      goto next;
@@ -1460,7 +1589,7 @@
 	DWORD dwFlags,
 	LPSTRRET strRet)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	CHAR		szPath[MAX_PATH]= "";
 		
@@ -1479,7 +1608,7 @@
 	}
 	else
 	{ 
-	  if (!SUCCEEDED(SHELL32_GetDisplayNameOfChild((IShellFolder2*)This, pidl, dwFlags, szPath, MAX_PATH)))
+	  if (!SUCCEEDED(SHELL32_GetDisplayNameOfChild(iface, pidl, dwFlags, szPath, MAX_PATH)))
 	    return E_OUTOFMEMORY;
 	}
 	strRet->uType = STRRET_CSTRA;
@@ -1494,7 +1623,7 @@
 	IShellFolder2 * iface,
 	GUID *pguid)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1502,7 +1631,7 @@
 	IShellFolder2 * iface,
 	IEnumExtraSearch **ppenum)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1512,7 +1641,7 @@
 	ULONG *pSort,
 	ULONG *pDisplay)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	TRACE("(%p)\n",This);
 
@@ -1526,7 +1655,7 @@
 	UINT iColumn,
 	DWORD *pcsFlags)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	
 	TRACE("(%p)\n",This);
 
@@ -1542,7 +1671,7 @@
 	const SHCOLUMNID *pscid,
 	VARIANT *pv)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 
 	return E_NOTIMPL;
@@ -1553,7 +1682,7 @@
 	UINT iColumn,
 	SHELLDETAILS *psd)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	HRESULT hr = E_FAIL;;
 
 	TRACE("(%p)->(%p %i %p)\n",This, pidl, iColumn, psd);
@@ -1586,7 +1715,7 @@
 	      _ILGetFileDate(pidl, psd->str.u.cStr, MAX_PATH);
 	      break;
 	    case 4:	/* attributes */
-	      _ILGetAttributeStr(pidl, psd->str.u.cStr, MAX_PATH);
+	      _ILGetFileAttributes(pidl, psd->str.u.cStr, MAX_PATH);
 	      break;
 	  }
 	  hr = S_OK;
@@ -1600,7 +1729,7 @@
 	LPCWSTR pwszName,
 	SHCOLUMNID *pscid)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1658,15 +1787,17 @@
 	sf=(IGenericSFImpl*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IGenericSFImpl));
 	sf->ref=1;
 
-	ICOM_VTBL(sf) = &sfmcvt;
+	ICOM_VTBL(sf)=&unkvt;
+	sf->lpvtblShellFolder=&sfmcvt;
 	sf->lpvtblPersistFolder = &psfvt;
 	sf->pclsid = (CLSID*)&CLSID_SFMyComp;
 	sf->absPidl=_ILCreateMyComputer();	/* my qualified pidl */
+	sf->pUnkOuter = (IUnknown *) &sf->lpVtbl;
 
 	TRACE("(%p)\n",sf);
 
 	shell32_ObjCount++;
-	return (IShellFolder *)sf;
+	return _IShellFolder_(sf);
 }
 
 /**************************************************************************
@@ -1681,7 +1812,7 @@
 	LPITEMIDLIST *ppidl,
 	DWORD *pdwAttributes)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	HRESULT		hr = E_OUTOFMEMORY;
 	LPCWSTR		szNext=NULL;
@@ -1704,7 +1835,7 @@
 
 	  if (szNext && *szNext)
 	  {
-	    hr = SHELL32_ParseNextElement(hwndOwner, (IShellFolder2*)This, &pidlTemp, (LPOLESTR)szNext, pchEaten, pdwAttributes);
+	    hr = SHELL32_ParseNextElement(hwndOwner, iface, &pidlTemp, (LPOLESTR)szNext, pchEaten, pdwAttributes);
 	  }
 	  else
 	  {
@@ -1727,7 +1858,7 @@
 	DWORD dwFlags,
 	LPENUMIDLIST* ppEnumIDList)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	TRACE("(%p)->(HWND=0x%08x flags=0x%08lx pplist=%p)\n",This,hwndOwner,dwFlags,ppEnumIDList);
 
@@ -1747,7 +1878,7 @@
 static HRESULT WINAPI ISF_MyComputer_fnBindToObject( IShellFolder2 * iface, LPCITEMIDLIST pidl,
 			LPBC pbcReserved, REFIID riid, LPVOID * ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	GUID		const * clsid;
 	char		xriid[50];
 	IShellFolder	*pShellFolder, *pSubFolder;
@@ -1761,7 +1892,7 @@
 
 	*ppvOut = NULL;
 
-	if ((clsid=_ILGetGUIDPointer(pidl)) && !IsEqualIID(clsid, &IID_MyComputer))
+	if ((clsid=_ILGetGUIDPointer(pidl)) && !IsEqualIID(clsid, &CLSID_MyComputer))
 	{
 	   if (!SUCCEEDED(SHELL32_CoCreateInitSF (This->absPidl, pidl, clsid, riid, (LPVOID*)&pShellFolder)))
 	   {
@@ -1773,7 +1904,7 @@
 	  if (!_ILIsDrive(pidl)) return E_INVALIDARG;
 
 	  pidltemp = ILCloneFirst(pidl);
-	  pShellFolder = IShellFolder_Constructor((IShellFolder*)This, pidltemp);
+	  pShellFolder = IShellFolder_Constructor(iface, pidltemp);
 	  ILFree(pidltemp);
 	}
 
@@ -1799,7 +1930,7 @@
 static HRESULT WINAPI ISF_MyComputer_fnCreateViewObject( IShellFolder2 * iface,
 		 HWND hwndOwner, REFIID riid, LPVOID *ppvOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	LPSHELLVIEW	pShellView;
 	char		xriid[50];
@@ -1824,7 +1955,7 @@
 	  }
 	  else if(IsEqualIID(riid, &IID_IShellView))
 	  {
-	    pShellView = IShellView_Constructor((IShellFolder *) This);
+	    pShellView = IShellView_Constructor((IShellFolder*)iface);
 	    if(pShellView)
 	    {
 	      hr = IShellView_QueryInterface(pShellView, riid, ppvOut);
@@ -1841,7 +1972,7 @@
 */
 static HRESULT WINAPI ISF_MyComputer_fnGetAttributesOf(IShellFolder2 * iface,UINT cidl,LPCITEMIDLIST *apidl,DWORD *rgfInOut)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	GUID		const * clsid;
 	DWORD		attributes;
@@ -1894,7 +2025,7 @@
 	DWORD dwFlags,
 	LPSTRRET strRet)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	char		szPath[MAX_PATH], szDrive[18];
 	int		len = 0;
@@ -1946,7 +2077,7 @@
 	  PathAddBackslashA(szPath);
 	  len = strlen(szPath);
 
-	  if (!SUCCEEDED(SHELL32_GetDisplayNameOfChild((IShellFolder2*)This, pidl, dwFlags | SHGDN_FORPARSING, szPath + len, MAX_PATH - len)))
+	  if (!SUCCEEDED(SHELL32_GetDisplayNameOfChild(iface, pidl, dwFlags | SHGDN_FORPARSING, szPath + len, MAX_PATH - len)))
 	    return E_OUTOFMEMORY;
 	}
 	strRet->uType = STRRET_CSTRA;
@@ -1961,7 +2092,7 @@
 	IShellFolder2 * iface,
 	GUID *pguid)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1969,7 +2100,7 @@
 	IShellFolder2 * iface,
 	IEnumExtraSearch **ppenum)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -1979,7 +2110,7 @@
 	ULONG *pSort,
 	ULONG *pDisplay)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 
 	TRACE("(%p)\n",This);
 
@@ -1993,7 +2124,7 @@
 	UINT iColumn,
 	DWORD *pcsFlags)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	
 	TRACE("(%p)\n",This);
 
@@ -2009,7 +2140,7 @@
 	const SHCOLUMNID *pscid,
 	VARIANT *pv)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 
 	return E_NOTIMPL;
@@ -2022,7 +2153,7 @@
 	UINT iColumn,
 	SHELLDETAILS *psd)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	HRESULT hr;
 
 	TRACE("(%p)->(%p %i %p)\n",This, pidl, iColumn, psd);
@@ -2079,7 +2210,7 @@
 	LPCWSTR pwszName,
 	SHCOLUMNID *pscid)
 {
-	ICOM_THIS(IGenericSFImpl, iface);
+	_ICOM_THIS_From_IShellFolder2(IGenericSFImpl, iface)
 	FIXME("(%p)\n",This);
 	return E_NOTIMPL;
 }	
@@ -2125,7 +2256,7 @@
 
 	TRACE("(%p)\n", This);
 
-	return IShellFolder_QueryInterface((IShellFolder*)This, iid, ppvObj);
+	return IUnknown_QueryInterface(This->pUnkOuter, iid, ppvObj);
 }
 
 /************************************************************************
@@ -2135,11 +2266,11 @@
 static ULONG WINAPI ISFPersistFolder_AddRef(
 	IPersistFolder *	iface)
 {
-	_ICOM_THIS_From_IPersistFolder(IShellFolder, iface);
+	_ICOM_THIS_From_IPersistFolder(IGenericSFImpl, iface);
 
 	TRACE("(%p)\n", This);
 
-	return IShellFolder_AddRef((IShellFolder*)This);
+	return IUnknown_AddRef(This->pUnkOuter);
 }
 
 /************************************************************************
@@ -2153,7 +2284,7 @@
 
 	TRACE("(%p)\n", This);
 
-	return IShellFolder_Release((IShellFolder*)This);
+	return IUnknown_Release(This->pUnkOuter);
 }
 
 /************************************************************************
@@ -2183,16 +2314,35 @@
 	IPersistFolder *	iface,
 	LPCITEMIDLIST		pidl)
 {
+	char sTemp[MAX_PATH];
 	_ICOM_THIS_From_IPersistFolder(IGenericSFImpl, iface);
 
-	TRACE("(%p)\n", This);
+	TRACE("(%p)->(%p)\n", This, pidl);
 
+	/* free the old stuff */
 	if(This->absPidl)
 	{
 	  SHFree(This->absPidl);
 	  This->absPidl = NULL;
 	}
+	if(This->sMyPath)
+	{
+	  SHFree(This->sMyPath);
+	  This->sMyPath = NULL;
+	}
+
+	/* set my pidl */
 	This->absPidl = ILClone(pidl);
+
+	/* set my path */
+	if (SHGetPathFromIDListA(pidl, sTemp))
+	{
+	  This->sMyPath = SHAlloc(strlen(sTemp+1));
+	  strcpy(This->sMyPath, sTemp);
+	}
+
+	TRACE("--(%p)->(%s)\n", This, This->sMyPath);
+
 	return S_OK;
 }
 
@@ -2242,7 +2392,7 @@
 
 	TRACE("(%p)\n", This);
 
-	return IShellFolder_QueryInterface((IShellFolder*)This, riid, ppvObj);
+	return IUnknown_QueryInterface(This->pUnkOuter, riid, ppvObj);
 }
 
 static ULONG WINAPI ISFDropTarget_AddRef( IDropTarget *iface)
@@ -2251,7 +2401,7 @@
 
 	TRACE("(%p)\n", This);
 
-	return IShellFolder_AddRef((IShellFolder*)This);
+	return IUnknown_AddRef(This->pUnkOuter);
 }
 
 static ULONG WINAPI ISFDropTarget_Release( IDropTarget *iface)
@@ -2260,7 +2410,7 @@
 
 	TRACE("(%p)\n", This);
 
-	return IShellFolder_Release((IShellFolder*)This);
+	return IUnknown_Release(This->pUnkOuter);
 }
 
 static HRESULT WINAPI ISFDropTarget_DragEnter(
diff --git a/dlls/shell32/shlview.c b/dlls/shell32/shlview.c
index 457ff13..1566f54 100644
--- a/dlls/shell32/shlview.c
+++ b/dlls/shell32/shlview.c
@@ -417,8 +417,8 @@
         /* Sort by Attribute: Folder or Files can be sorted */
         else if(pSortInfo->nHeaderID == LISTVIEW_COLUMN_ATTRIB)
         {
-            _ILGetAttributeStr(pItemIdList1, strName1, MAX_PATH);
-            _ILGetAttributeStr(pItemIdList2, strName2, MAX_PATH);
+            _ILGetFileAttributes(pItemIdList1, strName1, MAX_PATH);
+            _ILGetFileAttributes(pItemIdList2, strName2, MAX_PATH);
             nDiff = strcasecmp(strName1, strName2);
         }
         /* Sort by FileName: Folder or Files can be sorted */
diff --git a/include/shlguid.h b/include/shlguid.h
index a17dcaf..05e3de8 100644
--- a/include/shlguid.h
+++ b/include/shlguid.h
@@ -31,15 +31,17 @@
 DEFINE_GUID (IID_IDockingWindowSite,	0x2A342FC2L, 0x7B26, 0x11D0, 0x8C, 0xA9, 0x00, 0xA0, 0xC9, 0x2D, 0xBF, 0xE8);
 
 /****************************************************************************
-*  undocumented stuff
-*/
-/* the next IID's are the namespace elements of the pidls */
-DEFINE_GUID (IID_MyComputer,	0x20D04FE0L, 0x3AEA, 0x1069, 0xA2, 0xD8, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
-DEFINE_GUID (IID_IExplore,	0x871C5380L, 0x42A0, 0x1069, 0xA2, 0xEA, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
-DEFINE_GUID (IID_Control,	0x23EC2020L, 0x3AEA, 0x1069, 0xA2, 0xDD, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
-DEFINE_GUID (IID_Printer,	0x2227A280L, 0x3AEA, 0x1069, 0xA2, 0xDE, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
-DEFINE_GUID (IID_Network,	0x208D2C60L, 0x3AEA, 0x1069, 0xA2, 0xD7, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
-DEFINE_GUID (IID_BitBucket,	0x645FF040L, 0x5081, 0x101B, 0x9F, 0x08, 0x00, 0xAA, 0x00, 0x2F, 0x95, 0x4E);
-
-DEFINE_GUID (CLSID_PaperBin,	0x645FF040L, 0x5081, 0x101B, 0x9F, 0x08, 0x00, 0xAA, 0x00, 0x2F, 0x95, 0x4E);
+ * the next IID's are the namespace elements of the pidls
+ */
+DEFINE_GUID(CLSID_NetworkPlaces, 0x208D2C60, 0x3AEA, 0x1069, 0xA2, 0xD7, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
+DEFINE_GUID(CLSID_NetworkDomain, 0x46e06680, 0x4bf0, 0x11d1, 0x83, 0xee, 0x00, 0xa0, 0xc9, 0x0d, 0xc8, 0x49);
+DEFINE_GUID(CLSID_NetworkServer, 0xc0542a90, 0x4bf0, 0x11d1, 0x83, 0xee, 0x00, 0xa0, 0xc9, 0x0d, 0xc8, 0x49);
+DEFINE_GUID(CLSID_NetworkShare, 0x54a754c0, 0x4bf0, 0x11d1, 0x83, 0xee, 0x00, 0xa0, 0xc9, 0x0d, 0xc8, 0x49);
+DEFINE_GUID(CLSID_MyComputer, 0x20D04FE0, 0x3AEA, 0x1069, 0xA2, 0xD8, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
+DEFINE_GUID(CLSID_Internet, 0x871C5380, 0x42A0, 0x1069, 0xA2, 0xEA, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
+DEFINE_GUID(CLSID_ShellFSFolder, 0xF3364BA0, 0x65B9, 0x11CE, 0xA9, 0xBA, 0x00, 0xAA, 0x00, 0x4A, 0xE8, 0x37);
+DEFINE_GUID(CLSID_RecycleBin, 0x645FF040, 0x5081, 0x101B, 0x9F, 0x08, 0x00, 0xAA, 0x00, 0x2F, 0x95, 0x4E);
+DEFINE_GUID(CLSID_ControlPanel, 0x21EC2020, 0x3AEA, 0x1069, 0xA2, 0xDD, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
+DEFINE_GUID(CLSID_Printers, 0x2227A280, 0x3AEA, 0x1069, 0xA2, 0xDE, 0x08, 0x00, 0x2B, 0x30, 0x30, 0x9D);
+DEFINE_GUID(CLSID_MyDocuments, 0x450d8fba, 0xad25, 0x11d0, 0x98, 0xa8, 0x08, 0x00, 0x36, 0x1b, 0x11, 0x03);
 #endif /* __WINE_SHLGUID_H */