summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGeorge Hazan <ghazan@miranda.im>2020-09-08 13:21:50 +0300
committerGeorge Hazan <ghazan@miranda.im>2020-09-08 13:21:50 +0300
commit5d0dff54982b174d382aca8da00393273bc7b3e5 (patch)
treeb18df845cd408a8f4d32fe02e9e65109e01c58c0
parent7997d0ec5810ad7699d0de6417510ab756be320d (diff)
DeleteDirectoryTreeW - new function that deletes a folder with all subfolders (recursively)
-rw-r--r--include/m_utils.h6
-rw-r--r--libs/win32/mir_core.libbin467778 -> 468024 bytes
-rw-r--r--libs/win64/mir_core.libbin472746 -> 472972 bytes
-rw-r--r--plugins/BasicHistory/src/EventList.cpp3
-rw-r--r--plugins/BasicHistory/src/RichHtmlExport.cpp29
-rw-r--r--plugins/BasicHistory/src/Scheduler.cpp15
-rw-r--r--plugins/PackUpdater/Src/Events.cpp16
-rw-r--r--plugins/PluginUpdater/pu_stub/src/pu_stub.cpp32
-rw-r--r--plugins/PluginUpdater/pu_stub/src/stdafx.h1
-rw-r--r--plugins/PluginUpdater/src/Events.cpp16
-rw-r--r--plugins/Toaster/src/main.cpp14
-rw-r--r--src/mir_app/src/db_ini.cpp15
-rw-r--r--src/mir_app/src/profilemanager.cpp24
-rw-r--r--src/mir_core/src/mir_core.def1
-rw-r--r--src/mir_core/src/mir_core64.def1
-rw-r--r--src/mir_core/src/path.cpp24
16 files changed, 85 insertions, 112 deletions
diff --git a/include/m_utils.h b/include/m_utils.h
index d4cfd13593..f2e3095a31 100644
--- a/include/m_utils.h
+++ b/include/m_utils.h
@@ -291,6 +291,12 @@ EXTERN_C MIR_CORE_DLL(int) CreateDirectoryTree(const char *pszDir);
EXTERN_C MIR_CORE_DLL(int) CreateDirectoryTreeW(const wchar_t *pwszDir);
/////////////////////////////////////////////////////////////////////////////////////////
+// Deletes a directory recursively
+// Returns 0 on success or an error code otherwise
+
+EXTERN_C MIR_CORE_DLL(int) DeleteDirectoryTreeW(const wchar_t *pwszDir, bool bAllowUndo = false);
+
+/////////////////////////////////////////////////////////////////////////////////////////
// Creates all subdirectories required to create a file with the file name given
// Returns 0 on success or an error code otherwise
diff --git a/libs/win32/mir_core.lib b/libs/win32/mir_core.lib
index 285fb86cce..6b94777513 100644
--- a/libs/win32/mir_core.lib
+++ b/libs/win32/mir_core.lib
Binary files differ
diff --git a/libs/win64/mir_core.lib b/libs/win64/mir_core.lib
index 77dd4887cb..b4048c214b 100644
--- a/libs/win64/mir_core.lib
+++ b/libs/win64/mir_core.lib
Binary files differ
diff --git a/plugins/BasicHistory/src/EventList.cpp b/plugins/BasicHistory/src/EventList.cpp
index f6d03409dd..b686dbc998 100644
--- a/plugins/BasicHistory/src/EventList.cpp
+++ b/plugins/BasicHistory/src/EventList.cpp
@@ -26,7 +26,6 @@ extern int iconsNum;
static mir_cs csEventList;
-bool DeleteDirectory(LPCTSTR lpszDir, bool noRecycleBin = true);
std::wstring GetName(const std::wstring &path);
HistoryEventList::HistoryEventList() :
@@ -608,7 +607,7 @@ void HistoryEventList::Init()
GetTempPath(MAX_PATH, temp);
m_contactFileDir = temp;
m_contactFileDir += L"BasicHistoryImportDir\\";
- DeleteDirectory(m_contactFileDir.c_str());
+ DeleteDirectoryTreeW(m_contactFileDir.c_str());
CreateDirectory(m_contactFileDir.c_str(), nullptr);
}
diff --git a/plugins/BasicHistory/src/RichHtmlExport.cpp b/plugins/BasicHistory/src/RichHtmlExport.cpp
index bc316393d8..dc712cc1f2 100644
--- a/plugins/BasicHistory/src/RichHtmlExport.cpp
+++ b/plugins/BasicHistory/src/RichHtmlExport.cpp
@@ -253,39 +253,12 @@ void IcoSave(const std::wstring &fileName, HICON hicon)
if (ii.hbmMask) DeleteObject(ii.hbmMask);
}
-bool DeleteDirectory(LPCTSTR lpszDir, bool noRecycleBin = true)
-{
- size_t len = mir_wstrlen(lpszDir);
- wchar_t *pszFrom = new wchar_t[len + 2];
- wcscpy_s(pszFrom, len + 2, lpszDir);
- pszFrom[len] = 0;
- pszFrom[len + 1] = 0;
-
- SHFILEOPSTRUCT fileop;
- fileop.hwnd = nullptr; // no status display
- fileop.wFunc = FO_DELETE; // delete operation
- fileop.pFrom = pszFrom; // source file name as double null terminated string
- fileop.pTo = nullptr; // no destination needed
- fileop.fFlags = FOF_NOCONFIRMATION | FOF_SILENT; // do not prompt the user
-
- if (!noRecycleBin)
- fileop.fFlags |= FOF_ALLOWUNDO;
-
- fileop.fAnyOperationsAborted = FALSE;
- fileop.lpszProgressTitle = nullptr;
- fileop.hNameMappings = nullptr;
-
- int ret = SHFileOperation(&fileop);
- delete[] pszFrom;
- return (ret == 0);
-}
-
void RichHtmlExport::WriteHeader(const std::wstring &fileName, const std::wstring &filterName, const std::wstring &myName, const std::wstring &myId, const std::wstring &name1, const std::wstring &proto1, const std::wstring &id1, const std::string& baseProto1, const std::wstring& encoding)
{
baseProto = baseProto1;
folder = RemoveExt(fileName) + L"_files";
folderName = GetName(folder);
- DeleteDirectory(folder.c_str());
+ DeleteDirectoryTreeW(folder.c_str());
CreateDirectory(folder.c_str(), nullptr);
std::wstring css = folder + L"\\history.css";
BOOL cssCopied = FALSE;
diff --git a/plugins/BasicHistory/src/Scheduler.cpp b/plugins/BasicHistory/src/Scheduler.cpp
index a080d18e0e..51cce458ec 100644
--- a/plugins/BasicHistory/src/Scheduler.cpp
+++ b/plugins/BasicHistory/src/Scheduler.cpp
@@ -26,7 +26,6 @@ bool IsValidTask(TaskOptions& to, std::list<TaskOptions>* top = nullptr, std::ws
std::wstring GetFileName(const std::wstring &baseName, std::wstring contactName, std::map<std::wstring, bool>& existingContacts, bool replaceContact);
std::wstring GetDirectoryName(const std::wstring &path);
std::wstring GetName(const std::wstring &path);
-bool DeleteDirectory(LPCTSTR lpszDir, bool noRecycleBin = true);
void ListDirectory(const std::wstring &basePath, const std::wstring &path, std::list<std::wstring>& files);
std::wstring ReplaceStr(const std::wstring& str, wchar_t oldCh, wchar_t newCh);
time_t GetNextExportTime(TaskOptions& to);
@@ -286,7 +285,7 @@ bool DoTask(TaskOptions& to)
if (pos < dir.length())
dir = dir.substr(0, pos);
- DeleteDirectory(dir.c_str());
+ DeleteDirectoryTreeW(dir.c_str());
CreateDirectory(dir.c_str(), nullptr);
}
@@ -416,7 +415,7 @@ bool DoTask(TaskOptions& to)
}
if (to.useFtp || to.compress)
- DeleteDirectory(dir.c_str());
+ DeleteDirectoryTreeW(dir.c_str());
}
else {
std::map<std::wstring, bool> existingContacts;
@@ -440,7 +439,7 @@ bool DoTask(TaskOptions& to)
if (pos < dir.length())
dir = dir.substr(0, pos);
- DeleteDirectory(dir.c_str());
+ DeleteDirectoryTreeW(dir.c_str());
CreateDirectory(dir.c_str(), nullptr);
filePath = dir + L"\\" + filePath;
}
@@ -490,7 +489,7 @@ bool DoTask(TaskOptions& to)
if (error) {
if (to.compress && !to.useFtp)
- DeleteDirectory(dir.c_str());
+ DeleteDirectoryTreeW(dir.c_str());
}
else if (to.compress) {
std::wstring zipFilePath = to.filePath;
@@ -508,7 +507,7 @@ bool DoTask(TaskOptions& to)
zipDir = temp;
zipDir += L"zip<date>";
zipDir = GetFileName(zipDir, L"", existingContacts, true);
- DeleteDirectory(zipDir.c_str());
+ DeleteDirectoryTreeW(zipDir.c_str());
CreateDirectory(zipDir.c_str(), nullptr);
zipFilePath = zipDir + L"\\" + zipFilePath;
}
@@ -533,7 +532,7 @@ bool DoTask(TaskOptions& to)
}
}
- DeleteDirectory(dir.c_str());
+ DeleteDirectoryTreeW(dir.c_str());
}
}
@@ -966,7 +965,7 @@ bool ZipFiles(const std::wstring &dir, std::wstring zipFilePath, const std::stri
else error = true;
}
- DeleteDirectory(dir.c_str());
+ DeleteDirectoryTreeW(dir.c_str());
return error;
}
diff --git a/plugins/PackUpdater/Src/Events.cpp b/plugins/PackUpdater/Src/Events.cpp
index 3745f37732..0a59c5b14a 100644
--- a/plugins/PackUpdater/Src/Events.cpp
+++ b/plugins/PackUpdater/Src/Events.cpp
@@ -51,21 +51,9 @@ INT_PTR MenuCommand(WPARAM, LPARAM)
return 0;
}
-INT_PTR EmptyFolder(WPARAM, LPARAM lParam)
+INT_PTR EmptyFolder(WPARAM, LPARAM)
{
- SHFILEOPSTRUCT file_op = {
- nullptr,
- FO_DELETE,
- tszRoot,
- L"",
- FOF_NOERRORUI |
- FOF_SILENT,
- false,
- nullptr,
- L"" };
- if (lParam)
- file_op.fFlags |= FOF_NOCONFIRMATION;
- SHFileOperation(&file_op);
+ DeleteDirectoryTreeW(tszRoot);
return 0;
}
diff --git a/plugins/PluginUpdater/pu_stub/src/pu_stub.cpp b/plugins/PluginUpdater/pu_stub/src/pu_stub.cpp
index 60c67f7c1a..c3cd302482 100644
--- a/plugins/PluginUpdater/pu_stub/src/pu_stub.cpp
+++ b/plugins/PluginUpdater/pu_stub/src/pu_stub.cpp
@@ -21,8 +21,9 @@ void log(const wchar_t *tszFormat, ...)
int CreateDirectoryTreeW(const wchar_t* szDir)
{
- wchar_t szTestDir[MAX_PATH];
- lstrcpynW(szTestDir, szDir, MAX_PATH);
+ wchar_t szTestDir[MAX_PATH+1];
+ if (lstrcpynW(szTestDir, szDir, MAX_PATH) == nullptr)
+ szTestDir[MAX_PATH] = 0;
DWORD dwAttributes = GetFileAttributesW(szTestDir);
if (dwAttributes != INVALID_FILE_ATTRIBUTES && (dwAttributes & FILE_ATTRIBUTE_DIRECTORY))
@@ -38,6 +39,28 @@ int CreateDirectoryTreeW(const wchar_t* szDir)
return (CreateDirectoryW(szTestDir, nullptr) == 0) ? GetLastError() : 0;
}
+int DeleteDirectoryTreeW(const wchar_t *pwszDirName)
+{
+ // file name shall be double sero ended
+ wchar_t wszPath[MAX_PATH + 2];
+ if (lstrcpynW(wszPath, pwszDirName, MAX_PATH) == nullptr)
+ wszPath[MAX_PATH] = 0;
+ wszPath[lstrlenW(wszPath) + 1] = 0;
+
+ SHFILEOPSTRUCTW file_op = {
+ NULL,
+ FO_DELETE,
+ wszPath,
+ L"",
+ FOF_NOCONFIRMATION |
+ FOF_NOERRORUI |
+ FOF_SILENT,
+ false,
+ 0,
+ L"" };
+ return SHFileOperationW(&file_op);
+}
+
void CreatePathToFileW(wchar_t *wszFilePath)
{
wchar_t* pszLastBackslash = wcsrchr(wszFilePath, '\\');
@@ -132,6 +155,11 @@ int APIENTRY wWinMain(HINSTANCE /*hInstance*/, HINSTANCE, LPTSTR lpCmdLine, int)
dwError = 0;
break;
+ case 6: // delete folder recursively
+ DeleteDirectoryTreeW(ptszFile1);
+ dwError = 0;
+ break;
+
default:
dwError = ERROR_UNKNOWN_FEATURE;
}
diff --git a/plugins/PluginUpdater/pu_stub/src/stdafx.h b/plugins/PluginUpdater/pu_stub/src/stdafx.h
index b6f494b071..7ad5b19462 100644
--- a/plugins/PluginUpdater/pu_stub/src/stdafx.h
+++ b/plugins/PluginUpdater/pu_stub/src/stdafx.h
@@ -22,6 +22,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
+#include <shellapi.h>
// C RunTime Header Files
#include <stdlib.h>
diff --git a/plugins/PluginUpdater/src/Events.cpp b/plugins/PluginUpdater/src/Events.cpp
index 4c808600dc..55a28341bd 100644
--- a/plugins/PluginUpdater/src/Events.cpp
+++ b/plugins/PluginUpdater/src/Events.cpp
@@ -30,20 +30,6 @@ int OnFoldersChanged(WPARAM, LPARAM)
return 0;
}
-void EmptyFolder()
-{
- SHFILEOPSTRUCT file_op = {
- nullptr,
- FO_DELETE,
- g_wszRoot,
- L"",
- FOF_NOERRORUI | FOF_SILENT | FOF_NOCONFIRMATION,
- false,
- nullptr,
- L"" };
- SHFileOperation(&file_op);
-}
-
int ModulesLoaded(WPARAM, LPARAM)
{
if (hPluginUpdaterFolder = FoldersRegisterCustomPathW(MODULEA, LPGEN("Plugin Updater"), MIRANDA_PATHW L"\\" DEFAULT_UPDATES_FOLDER)) {
@@ -59,7 +45,7 @@ int ModulesLoaded(WPARAM, LPARAM)
if (iRestartCount > 0)
g_plugin.setByte(DB_SETTING_RESTART_COUNT, iRestartCount - 1);
else
- EmptyFolder(); // silently
+ DeleteDirectoryTreeW(g_wszRoot);
CheckUpdateOnStartup();
diff --git a/plugins/Toaster/src/main.cpp b/plugins/Toaster/src/main.cpp
index 470399a83d..10dea8e278 100644
--- a/plugins/Toaster/src/main.cpp
+++ b/plugins/Toaster/src/main.cpp
@@ -31,19 +31,7 @@ extern "C" __declspec(dllexport) const MUUID MirandaInterfaces[] = { MIID_POPUP,
static int OnPreShutdown(WPARAM, LPARAM)
{
CleanupClasses();
-
- SHFILEOPSTRUCT file_op = {
- nullptr,
- FO_DELETE,
- wszTempDir,
- L"",
- FOF_NOERRORUI | FOF_SILENT | FOF_NOCONFIRMATION,
- false,
- nullptr,
- L""
- };
- SHFileOperation(&file_op);
-
+ DeleteDirectoryTreeW(wszTempDir);
return 0;
}
diff --git a/src/mir_app/src/db_ini.cpp b/src/mir_app/src/db_ini.cpp
index 2580d8eb3d..f7122100e0 100644
--- a/src/mir_app/src/db_ini.cpp
+++ b/src/mir_app/src/db_ini.cpp
@@ -216,13 +216,7 @@ protected:
void Recycle_OnClick(CCtrlBase*)
{
- ptrW szIniPath(m_iniPath.GetText());
- SHFILEOPSTRUCT shfo = {};
- shfo.wFunc = FO_DELETE;
- shfo.pFrom = szIniPath;
- szIniPath[mir_wstrlen(szIniPath) + 1] = '\0';
- shfo.fFlags = FOF_NOCONFIRMATION | FOF_NOERRORUI | FOF_SILENT | FOF_ALLOWUNDO;
- SHFileOperation(&shfo);
+ DeleteDirectoryTreeW(ptrW(m_iniPath.GetText()), true);
Close();
}
@@ -553,12 +547,7 @@ static void DoAutoExec(void)
if (!mir_wstrcmpi(szOnCompletion, L"delete"))
DeleteFile(szIniPath);
else if (!mir_wstrcmpi(szOnCompletion, L"recycle")) {
- SHFILEOPSTRUCT shfo = {};
- shfo.wFunc = FO_DELETE;
- shfo.pFrom = szIniPath;
- szIniPath[mir_wstrlen(szIniPath) + 1] = 0;
- shfo.fFlags = FOF_NOCONFIRMATION | FOF_NOERRORUI | FOF_SILENT | FOF_ALLOWUNDO;
- SHFileOperation(&shfo);
+ DeleteDirectoryTreeW(szIniPath, true);
}
else if (!mir_wstrcmpi(szOnCompletion, L"rename")) {
wchar_t szRenamePrefix[MAX_PATH], szNewPath[MAX_PATH];
diff --git a/src/mir_app/src/profilemanager.cpp b/src/mir_app/src/profilemanager.cpp
index fc4912cf7b..96e802d6cf 100644
--- a/src/mir_app/src/profilemanager.cpp
+++ b/src/mir_app/src/profilemanager.cpp
@@ -84,14 +84,14 @@ class CCreateProfileDlg : public CDlgBase
int CreateProfile(const wchar_t *profile, DATABASELINK *link)
{
- wchar_t buf[256];
- int err = 0;
-
// check if the file already exists
const wchar_t *file = wcsrchr(profile, '\\');
if (file)
file++;
-
+
+ int err = 0;
+ wchar_t buf[256];
+
if (_waccess(profile, 0) == 0) {
// file already exists!
mir_snwprintf(buf,
@@ -101,12 +101,7 @@ class CCreateProfileDlg : public CDlgBase
return 0;
// move the file
- SHFILEOPSTRUCT sf = {};
- sf.wFunc = FO_DELETE;
- sf.pFrom = buf;
- sf.fFlags = FOF_NOCONFIRMATION | FOF_NOERRORUI | FOF_SILENT | FOF_ALLOWUNDO;
- mir_snwprintf(buf, L"%s\0", profile);
- if (SHFileOperation(&sf) != 0) {
+ if (DeleteDirectoryTreeW(profile, true) != 0) {
mir_snwprintf(buf, TranslateT("Couldn't move '%s' to the Recycle Bin. Please select another profile name."), file);
MessageBox(m_hwnd, buf, TranslateT("Problem moving profile"), MB_ICONINFORMATION | MB_OK);
return 0;
@@ -329,13 +324,8 @@ class CChooseProfileDlg : public CDlgBase
if (IDYES != MessageBoxW(nullptr, wszMessage, L"Miranda NG", MB_YESNO | MB_TASKMODAL | MB_ICONWARNING))
return;
- wszMessage.Format(L"%s\\%s%c", m_pd->ptszProfileDir, item.pszText, 0);
-
- SHFILEOPSTRUCT sf = {};
- sf.wFunc = FO_DELETE;
- sf.pFrom = wszMessage;
- sf.fFlags = FOF_NOCONFIRMATION | FOF_SILENT | FOF_ALLOWUNDO;
- SHFileOperation(&sf);
+ wszMessage.Format(L"%s\\%s", m_pd->ptszProfileDir, item.pszText);
+ DeleteDirectoryTreeW(wszMessage, true);
m_profileList.DeleteItem(item.iItem);
}
diff --git a/src/mir_core/src/mir_core.def b/src/mir_core/src/mir_core.def
index 1636bc0239..d0e17162d9 100644
--- a/src/mir_core/src/mir_core.def
+++ b/src/mir_core/src/mir_core.def
@@ -2,6 +2,7 @@ LIBRARY mir_core.mir
EXPORTS
?g_pCurrDb@@3PAVMDatabaseCommon@@A @1 NONAME
+DeleteDirectoryTreeW @2
CallFunctionAsync @5
CallPluginEventHook @7
CallService @8
diff --git a/src/mir_core/src/mir_core64.def b/src/mir_core/src/mir_core64.def
index bb77e99aac..797fb38dcd 100644
--- a/src/mir_core/src/mir_core64.def
+++ b/src/mir_core/src/mir_core64.def
@@ -2,6 +2,7 @@ LIBRARY mir_core.mir
EXPORTS
?g_pCurrDb@@3PEAVMDatabaseCommon@@EA @1 NONAME
+DeleteDirectoryTreeW @2
CallFunctionAsync @5
CallPluginEventHook @7
CallService @8
diff --git a/src/mir_core/src/path.cpp b/src/mir_core/src/path.cpp
index 99d95d9757..596eea39c4 100644
--- a/src/mir_core/src/path.cpp
+++ b/src/mir_core/src/path.cpp
@@ -207,6 +207,30 @@ MIR_CORE_DLL(int) CreateDirectoryTreeW(const wchar_t *szDir)
return (CreateDirectoryW(szTestDir, nullptr) == 0) ? GetLastError() : 0;
}
+MIR_CORE_DLL(int) DeleteDirectoryTreeW(const wchar_t *pwszDir, bool bAllowUndo)
+{
+ if (pwszDir == nullptr)
+ return ERROR_BAD_ARGUMENTS;
+
+ CMStringW wszPath(pwszDir);
+ wszPath.AppendChar(0);
+
+ SHFILEOPSTRUCTW file_op = {
+ nullptr,
+ FO_DELETE,
+ wszPath,
+ L"",
+ FOF_NOERRORUI | FOF_SILENT | FOF_NOCONFIRMATION,
+ false,
+ nullptr,
+ L"" };
+
+ if (bAllowUndo)
+ file_op.fFlags |= FOF_ALLOWUNDO;
+
+ return SHFileOperationW(&file_op);
+}
+
int InitPathUtils(void)
{
GetModuleFileNameA(nullptr, szMirandaPath, _countof(szMirandaPath));