在本地NTFS驱动器上查找回收站

我试图写一些简单的代码,将回收本地驱动器上回收站的目录。 看起来好像很简单 – 在Google上应该有一千个答案。 还没有find一个:(

我发现FAT和NTFS驱动器有不同的基本名称(RECYCLED和RECYCLER)。 我发现“回收站”是一个虚拟文件夹,它结合了机器上所有驱动器的回收站。

我没有find的是findC盘的回收站目录 – 即使在越南语(或任何其他非英语)的机器上。 (没有post,我可以find表明“RECYCLER”是否获得国际化)

任何人都可以指出我一个明确的答案?

谢谢

更新:意识到CSIDL_BITBUCKET和使用它的function。 从我读过的所有东西中,它指向一个虚拟目录,它是所有驱动器上该用户删除的所有文件的联合。 寻找物理回收站目录(在我的Vista上,它似乎是C:\ $ Recycle.Bin据我所知)

使用Raymond Chen的建议和别人的技术(不记得我在哪里找到它),我提供了一个可以在驱动器上找到Recycle Bin目录的函数。 该函数遍历根目录中的目录,查看隐藏和/或系统目录。 当它找到一个,它检查子子目录寻找一个有CLSID_Recycle Bin。

请注意,我已经在下面包含了两个GetFolderCLSID函数。 雷蒙德是更简单的,但它不适用于Windows 2000.其他实现更长,但似乎无处不在。

调用如:CString recycleDir = FindRecycleBinOnDrive(L“C:\”);

 CString FindRecycleBinOnDrive(LPCWSTR path) { CString search; search.Format(L"%c:\\*", path[0]); WIN32_FIND_DATA fd = {0}; HANDLE fHandle = FindFirstFile(search, &fd); while(INVALID_HANDLE_VALUE != fHandle) { if(FILE_ATTRIBUTE_DIRECTORY == (fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) //only check directories { if(0 != (fd.dwFileAttributes & (FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN))) //only check hidden and/or system directories { //the recycle bin directory itself won't be marked, but a SID-specific child directory will, so now look at them CString childSearch; childSearch.Format(L"%c:\\%s\\*", path[0], fd.cFileName); WIN32_FIND_DATA childFD = {0}; HANDLE childHandle = FindFirstFile(childSearch, &childFD); while(INVALID_HANDLE_VALUE != childHandle) { if((FILE_ATTRIBUTE_DIRECTORY == (childFD.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) && //only check directories (childFD.cFileName[0] != L'.')) //don't check . and .. dirs { CString fullPath; fullPath.Format(L"%c:\\%s\\%s", path[0], fd.cFileName, childFD.cFileName); CLSID id = {0}; HRESULT hr = GetFolderCLSID(fullPath, id); if(SUCCEEDED(hr)) { if(IsEqualGUID(CLSID_RecycleBin, id)) { FindClose(childHandle); FindClose(fHandle); //return the parent (recycle bin) directory fullPath.Format(L"%c:\\%s", path[0], fd.cFileName); return fullPath; } } else { Log(logERROR, L"GetFolderCLSID returned %08X for %s", hr, fullPath); } } if(FALSE == FindNextFile(childHandle, &childFD)) { FindClose(childHandle); childHandle = INVALID_HANDLE_VALUE; } } } } if(FALSE == FindNextFile(fHandle, &fd)) { FindClose(fHandle); fHandle = INVALID_HANDLE_VALUE; } } _ASSERT(0); return L""; } //Works on Windows 2000, and even as Local System account HRESULT GetFolderCLSID(LPCWSTR path, CLSID& pathCLSID) { LPMALLOC pMalloc = NULL; HRESULT hr = 0; if (SUCCEEDED(hr = SHGetMalloc(&pMalloc))) { LPSHELLFOLDER pshfDesktop = NULL; if (SUCCEEDED(hr = SHGetDesktopFolder(&pshfDesktop))) { LPITEMIDLIST pidl = NULL; DWORD dwAttributes = SFGAO_FOLDER; if (SUCCEEDED(hr = pshfDesktop->ParseDisplayName(NULL, NULL, (LPWSTR)path, NULL, &pidl, &dwAttributes))) { LPPERSIST pPersist = NULL; if (SUCCEEDED(hr = pshfDesktop->BindToObject(pidl, NULL, IID_IPersist, (LPVOID *) &pPersist))) { hr = pPersist->GetClassID(&pathCLSID); pPersist->Release(); } pMalloc->Free(pidl); } pshfDesktop->Release(); } pMalloc->Release(); } return hr; } //Not supported on Windows 2000 since SHParseDisplayName wasn't implemented then //HRESULT GetFolderCLSID(LPCWSTR pszPath, CLSID& pathCLSID) //{ // SHDESCRIPTIONID did = {0}; // HRESULT hr = 0; // LPITEMIDLIST pidl = NULL; // if (SUCCEEDED(hr = SHParseDisplayName(pszPath, NULL, &pidl, 0, NULL))) //not supported by Windows 2000 // { // IShellFolder *psf = NULL; // LPCITEMIDLIST pidlChild = NULL; // if (SUCCEEDED(hr = SHBindToParent(pidl, IID_IShellFolder, (void**)&psf, &pidlChild))) // { // hr = SHGetDataFromIDList(psf, pidlChild, SHGDFIL_DESCRIPTIONID, &did, sizeof(did)); // psf->Release(); // pathCLSID = did.clsid; // } // CoTaskMemFree(pidl); // } // return hr; //} 

Raymond Chen有答案 – 我怎么知道一个目录实际上是一个回收站 ?

晚了一点,但也许比从未更晚。

调试shell32.dll之后,我发现对于每个版本的Windows,回收路径都是硬编码的,并且还取决于该驱动器的文件系统。 我已经测试了这个在Windows XP,Vista和Windows7上:

让X:是我们想要获得回收站路径的驱动器,并且让SID是当前用户的SID,然后:

switchif(OsType) { case WindowsXP: { if(PartitionType("X:") == NTFS) { printf("Path is: X:\\Recycler\\SID\\"); } else { printf("Path is X:\\RECYCLED\\"); } } case WindowsVista: case Windows7: { if(PartitionType("X:") == NTFS) { printf("Path is: X:\\$Recycle.bin\\SID\\"); } else { printf("Path is X:\\$RECYCLE.BIN\\"); } } }
switchif(OsType) { case WindowsXP: { if(PartitionType("X:") == NTFS) { printf("Path is: X:\\Recycler\\SID\\"); } else { printf("Path is X:\\RECYCLED\\"); } } case WindowsVista: case Windows7: { if(PartitionType("X:") == NTFS) { printf("Path is: X:\\$Recycle.bin\\SID\\"); } else { printf("Path is X:\\$RECYCLE.BIN\\"); } } } 

维基文章提供了相同的事实: http : //en.wikipedia.org/wiki/Recycle_Bin_%28Windows%29

在Win32中,使用SHGetSpecialFolderLocation 。 传递CSIDL_BITBUCKET作为CDIL参数。