From cfafaee5b06ae9fb5a836e9e714f084c32540e95 Mon Sep 17 00:00:00 2001 From: Gunnar Beutner Date: Mon, 18 Apr 2016 15:33:20 +0200 Subject: [PATCH] Move user data before running the uninstaller refs #11449 --- icinga-installer/icinga-installer.cpp | 64 ++++++++++++++++++--------- 1 file changed, 44 insertions(+), 20 deletions(-) diff --git a/icinga-installer/icinga-installer.cpp b/icinga-installer/icinga-installer.cpp index 8e3b1d4bf..c024315b5 100644 --- a/icinga-installer/icinga-installer.cpp +++ b/icinga-installer/icinga-installer.cpp @@ -167,23 +167,32 @@ static void CollectPaths(std::vector& paths, const std::string& pat paths.push_back(path); } -static bool MoveDirectory(const std::string& source, const std::string& destination) +static bool CopyDirectory(const std::string& source, const std::string& destination) { - if (!MoveFileEx(source.c_str(), destination.c_str(), MOVEFILE_COPY_ALLOWED | MOVEFILE_WRITE_THROUGH)) { - // SHFileOperation requires file names to be terminated with two \0s - std::string tmpSource = source + std::string(1, '\0'); - std::string tmpDestination = destination + std::string(1, '\0'); + // SHFileOperation requires file names to be terminated with two \0s + std::string tmpSource = source + std::string(1, '\0'); + std::string tmpDestination = destination + std::string(1, '\0'); - SHFILEOPSTRUCT fop; - fop.wFunc = FO_COPY; - fop.pFrom = tmpSource.c_str(); - fop.pTo = tmpDestination.c_str(); - fop.fFlags = FOF_NO_UI; - if (SHFileOperation(&fop) != 0) - return false; - } + SHFILEOPSTRUCT fop; + fop.wFunc = FO_COPY; + fop.pFrom = tmpSource.c_str(); + fop.pTo = tmpDestination.c_str(); + fop.fFlags = FOF_NO_UI; + + return (SHFileOperation(&fop) == 0); +} - return true; +static bool DeleteDirectory(const std::string& dir) +{ + // SHFileOperation requires file names to be terminated with two \0s + std::string tmpDir = dir + std::string(1, '\0'); + + SHFILEOPSTRUCT fop; + fop.wFunc = FO_DELETE; + fop.pFrom = tmpDir.c_str(); + fop.fFlags = FOF_NO_UI; + + return (SHFileOperation(&fop) == 0); } static int UpgradeNSIS(void) @@ -198,24 +207,39 @@ static int UpgradeNSIS(void) if (!PathExists(uninstallerPath)) return 0; - ExecuteCommand(uninstallerPath, "/S _?=" + installPath); + std::string dataPath = GetIcingaDataPath(); - _unlink(uninstallerPath.c_str()); + if (dataPath.empty()) + return 1; - std::string dataPath = GetIcingaDataPath(); + bool moveUserData = !PathExists(dataPath); /* perform open heart surgery on the user's data dirs - yay */ - if (!PathExists(dataPath)) { + if (moveUserData) { MkDir(dataPath.c_str()); std::string oldNameEtc = installPath + "\\etc"; std::string newNameEtc = dataPath + "\\etc"; - if (!MoveDirectory(oldNameEtc, newNameEtc)) + if (!CopyDirectory(oldNameEtc, newNameEtc)) return 1; std::string oldNameVar = installPath + "\\var"; std::string newNameVar = dataPath + "\\var"; - if (!MoveDirectory(oldNameVar, newNameVar)) + if (!CopyDirectory(oldNameVar, newNameVar)) + return 1; + } + + ExecuteCommand(uninstallerPath, "/S _?=" + installPath); + + _unlink(uninstallerPath.c_str()); + + if (moveUserData) { + std::string oldNameEtc = installPath + "\\etc"; + if (!DeleteDirectory(oldNameEtc)) + return 1; + + std::string oldNameVar = installPath + "\\var"; + if (!DeleteDirectory(oldNameVar)) return 1; _rmdir(installPath.c_str()); -- 2.40.0