summaryrefslogtreecommitdiff
path: root/synchronization.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'synchronization.cpp')
-rw-r--r--synchronization.cpp98
1 files changed, 53 insertions, 45 deletions
diff --git a/synchronization.cpp b/synchronization.cpp
index 00330c6a..10ec2f5a 100644
--- a/synchronization.cpp
+++ b/synchronization.cpp
@@ -1,7 +1,7 @@
// **************************************************************************
// * This file is part of the FreeFileSync project. It is distributed under *
// * GNU General Public License: http://www.gnu.org/licenses/gpl.html *
-// * Copyright (C) 2008-2011 ZenJu (zhnmju123 AT gmx.de) *
+// * Copyright (C) ZenJu (zhnmju123 AT gmx DOT de) - All Rights Reserved *
// **************************************************************************
#include "synchronization.h"
@@ -866,34 +866,37 @@ private:
class zen::SynchronizeFolderPair
{
public:
- SynchronizeFolderPair(const SyncProcess& syncProc,
+ SynchronizeFolderPair(ProcessCallback& procCallback,
+ bool verifyCopiedFiles,
+ bool copyFilePermissions,
+ bool transactionalFileCopy,
#ifdef FFS_WIN
shadow::ShadowCopy* shadowCopyHandler,
#endif
const DeletionHandling& delHandlingLeft,
const DeletionHandling& delHandlingRight) :
- procCallback_(syncProc.procCallback),
+ procCallback_(procCallback),
#ifdef FFS_WIN
shadowCopyHandler_(shadowCopyHandler),
#endif
delHandlingLeft_(delHandlingLeft),
delHandlingRight_(delHandlingRight),
- verifyCopiedFiles(syncProc.verifyCopiedFiles_),
- copyFilePermissions(syncProc.copyFilePermissions_),
- transactionalFileCopy(syncProc.transactionalFileCopy_),
- txtCreatingFile (replaceCpy(_("Creating file %x" ), L"%x", L"\"%x\"", false)),
+ verifyCopiedFiles_(verifyCopiedFiles),
+ copyFilePermissions_(copyFilePermissions),
+ transactionalFileCopy_(transactionalFileCopy),
+ txtCreatingFile (replaceCpy(_("Creating file %x" ), L"%x", L"\"%x\"", false)), //harmonize with duplicates in CallbackMoveFileImpl!!!
txtCreatingLink (replaceCpy(_("Creating symbolic link %x" ), L"%x", L"\"%x\"", false)),
- txtCreatingFolder (replaceCpy(_("Creating folder %x" ), L"%x", L"\"%x\"", false)),
+ txtCreatingFolder (replaceCpy(_("Creating folder %x" ), L"%x", L"\"%x\"", false)), //
txtOverwritingFile (replaceCpy(_("Overwriting file %x" ), L"%x", L"\"%x\"", false)),
txtOverwritingLink (replaceCpy(_("Overwriting symbolic link %x"), L"%x", L"\"%x\"", false)),
txtVerifying (replaceCpy(_("Verifying file %x" ), L"%x", L"\"%x\"", false)),
txtWritingAttributes(replaceCpy(_("Updating attributes of %x" ), L"%x", L"\"%x\"", false)),
- txtMovingFile (replaceCpy(replaceCpy(_("Moving file %x to %y"), L"%x", L"\"%x\"", false), L"%y", L"\"%y\"", false)) {}
- //harmonize with duplicates in CallbackMoveFileImpl!!!
+ txtMovingFile (replaceCpy(replaceCpy(_("Moving file %x to %y"), L"%x", L"\"%x\"", false), L"%y", L"\"%y\"", false))
+ {}
void startSync(BaseDirMapping& baseMap)
{
- runZeroPass(baseMap); //first process file moves
+ runZeroPass(baseMap); //first process file moves
runPass<PASS_ONE>(baseMap); //delete files (or overwrite big ones with smaller ones)
runPass<PASS_TWO>(baseMap); //copy rest
}
@@ -947,9 +950,9 @@ private:
const DeletionHandling& delHandlingLeft_;
const DeletionHandling& delHandlingRight_;
- const bool verifyCopiedFiles;
- const bool copyFilePermissions;
- const bool transactionalFileCopy;
+ const bool verifyCopiedFiles_;
+ const bool copyFilePermissions_;
+ const bool transactionalFileCopy_;
//preload status texts
const std::wstring txtCreatingFile;
@@ -1569,7 +1572,7 @@ void SynchronizeFolderPair::synchronizeLinkInt(SymLinkMapping& linkObj, SyncOper
try
{
- zen::copySymlink(linkObj.getFullName<sideSrc>(), target, copyFilePermissions); //throw FileError
+ zen::copySymlink(linkObj.getFullName<sideSrc>(), target, copyFilePermissions_); //throw FileError
procCallback_.updateProcessedData(1, 0);
linkObj.copyTo<sideTrg>(); //update SymLinkMapping
@@ -1608,7 +1611,7 @@ void SynchronizeFolderPair::synchronizeLinkInt(SymLinkMapping& linkObj, SyncOper
linkObj.removeObject<sideTrg>(); //remove file from FileMapping, to keep in sync (if subsequent copying fails!!)
reportStatus(txtOverwritingLink, target); //restore status text
- zen::copySymlink(linkObj.getFullName<sideSrc>(), target, copyFilePermissions); //throw FileError
+ zen::copySymlink(linkObj.getFullName<sideSrc>(), target, copyFilePermissions_); //throw FileError
linkObj.copyTo<sideTrg>(); //update SymLinkMapping
procCallback_.updateProcessedData(1, 0);
@@ -1677,7 +1680,7 @@ void SynchronizeFolderPair::synchronizeFolderInt(DirMapping& dirObj, SyncOperati
const Zstring& target = dirObj.getBaseDirPf<sideTrg>() + dirObj.getRelativeName<sideSrc>();
reportInfo(txtCreatingFolder, target);
- createDirectory(target, dirObj.getFullName<sideSrc>(), copyFilePermissions); //no symlink copying!
+ createDirectory(target, dirObj.getFullName<sideSrc>(), copyFilePermissions_); //no symlink copying!
dirObj.copyTo<sideTrg>(); //update DirMapping
procCallback_.updateProcessedData(1, 0);
@@ -1843,10 +1846,10 @@ void SyncProcess::startSynchronizationProcess(const std::vector<FolderPairSyncCf
}
};
- typedef std::vector<std::pair<Zstring, Zstring> > DirPairList;
+ typedef std::vector<std::pair<Zstring, Zstring>> DirPairList;
DirPairList significantDiff;
- typedef std::vector<std::pair<Zstring, std::pair<zen::Int64, zen::Int64> > > DirSpaceRequAvailList; //dirname / space required / space available
+ typedef std::vector<std::pair<Zstring, std::pair<Int64, Int64>>> DirSpaceRequAvailList; //dirname / space required / space available
DirSpaceRequAvailList diskSpaceMissing;
std::set<Zstring> recyclMissing;
@@ -1925,7 +1928,7 @@ void SyncProcess::startSynchronizationProcess(const std::vector<FolderPairSyncCf
//check if user-defined directory for deletion was specified
if (folderPairCfg.custDelFolder.empty())
{
- procCallback.reportFatalError(_("User-defined directory for deletion was not specified!"));
+ procCallback.reportFatalError(_("Directory for file versioning was not supplied!"));
skipFolderPair[folderIndex] = true;
continue;
}
@@ -1956,28 +1959,24 @@ void SyncProcess::startSynchronizationProcess(const std::vector<FolderPairSyncCf
if (significantDifferenceDetected(folderPairStat))
significantDiff.push_back(std::make_pair(j->getBaseDirPf<LEFT_SIDE>(), j->getBaseDirPf<RIGHT_SIDE>()));
- //check for sufficient free diskspace in left directory
+ //check for sufficient free diskspace
+ auto checkSpace = [&](const Zstring& baseDirPf, const Int64& spaceRequired)
+ {
+ wxLongLong freeDiskSpace;
+ if (wxGetDiskSpace(toWx(baseDirPf), NULL, &freeDiskSpace))
+ {
+ if (0 < freeDiskSpace && //zero disk space is either an error or not: in both cases this warning message is obsolete (WebDav seems to report 0)
+ freeDiskSpace.GetValue() < spaceRequired)
+ diskSpaceMissing.push_back(std::make_pair(baseDirPf, std::make_pair(spaceRequired, freeDiskSpace.GetValue())));
+ }
+ };
const std::pair<Int64, Int64> spaceNeeded = DiskSpaceNeeded::calculate(*j, delHandlerFp.first.deletionFreesSpace(),
delHandlerFp.second.deletionFreesSpace());
- wxLongLong freeDiskSpaceLeft;
- if (wxGetDiskSpace(toWx(j->getBaseDirPf<LEFT_SIDE>()), NULL, &freeDiskSpaceLeft))
- {
- if (0 < freeDiskSpaceLeft && //zero disk space is either an error or not: in both cases this warning message is obsolete (WebDav seems to report 0)
- freeDiskSpaceLeft.ToDouble() < to<double>(spaceNeeded.first))
- diskSpaceMissing.push_back(std::make_pair(j->getBaseDirPf<LEFT_SIDE>(), std::make_pair(spaceNeeded.first, freeDiskSpaceLeft.ToDouble())));
- }
-
- //check for sufficient free diskspace in right directory
- wxLongLong freeDiskSpaceRight;
- if (wxGetDiskSpace(toWx(j->getBaseDirPf<RIGHT_SIDE>()), NULL, &freeDiskSpaceRight))
- {
- if (0 < freeDiskSpaceRight && //zero disk space is either an error or not: in both cases this warning message is obsolete (WebDav seems to report 0)
- freeDiskSpaceRight.ToDouble() < to<double>(spaceNeeded.second))
- diskSpaceMissing.push_back(std::make_pair(j->getBaseDirPf<RIGHT_SIDE>(), std::make_pair(spaceNeeded.second, freeDiskSpaceRight.ToDouble())));
- }
+ checkSpace(j->getBaseDirPf<LEFT_SIDE >(), spaceNeeded.first);
+ checkSpace(j->getBaseDirPf<RIGHT_SIDE>(), spaceNeeded.second);
- //windows: check if recycle bin really exists; if not, Windows will silently delete, which is wrong
#ifdef FFS_WIN
+ //windows: check if recycle bin really exists; if not, Windows will silently delete, which is wrong
if (folderPairCfg.handleDeletion == MOVE_TO_RECYCLE_BIN)
{
if (folderPairStat.getUpdate<LEFT_SIDE>() +
@@ -2138,7 +2137,7 @@ void SyncProcess::startSynchronizationProcess(const std::vector<FolderPairSyncCf
//execute synchronization recursively
//update synchronization database (automatic sync only)
- zen::ScopeGuard guardUpdateDb = zen::makeGuard([&]()
+ zen::ScopeGuard guardUpdateDb = zen::makeGuard([&]
{
if (folderPairCfg.inAutomaticMode)
zen::saveToDisk(*j); //throw FileError
@@ -2147,7 +2146,15 @@ void SyncProcess::startSynchronizationProcess(const std::vector<FolderPairSyncCf
//guarantee removal of invalid entries (where element on both sides is empty)
ZEN_ON_BLOCK_EXIT(BaseDirMapping::removeEmpty(*j););
- SynchronizeFolderPair syncFP(*this,
+ bool copyPermissionsFp = false;
+ tryReportingError(procCallback, [&]
+ {
+ copyPermissionsFp = copyFilePermissions_ && //copy permissions only if asked for and supported by *both* sides!
+ supportsPermissions(beforeLast(j->getBaseDirPf<LEFT_SIDE >(), FILE_NAME_SEPARATOR)) && //throw FileError
+ supportsPermissions(beforeLast(j->getBaseDirPf<RIGHT_SIDE>(), FILE_NAME_SEPARATOR));
+ }); //show error dialog if necessary
+
+ SynchronizeFolderPair syncFP(procCallback, verifyCopiedFiles_, copyPermissionsFp, transactionalFileCopy_,
#ifdef FFS_WIN
shadowCopyHandler.get(),
#endif
@@ -2156,13 +2163,14 @@ void SyncProcess::startSynchronizationProcess(const std::vector<FolderPairSyncCf
syncFP.startSync(*j);
//(try to gracefully) cleanup temporary folders (Recycle bin optimization) -> will be done in ~DeletionHandling anyway...
- tryReportingError(procCallback, [&]() { delHandlerFp.first .tryCleanup(); }); //show error dialog if necessary
- tryReportingError(procCallback, [&]() { delHandlerFp.second.tryCleanup(); }); //
+ tryReportingError(procCallback, [&] { delHandlerFp.first .tryCleanup(); }); //show error dialog if necessary
+ tryReportingError(procCallback, [&] { delHandlerFp.second.tryCleanup(); }); //
//(try to gracefully) write database file (will be done in ~EnforceUpdateDatabase anyway...)
if (folderPairCfg.inAutomaticMode)
{
procCallback.reportStatus(_("Generating database..."));
+ procCallback.forceUiRefresh();
tryReportingError(procCallback, [&]() { zen::saveToDisk(*j); }); //throw FileError
guardUpdateDb.dismiss();
@@ -2236,8 +2244,8 @@ void SynchronizeFolderPair::copyFileUpdatingTo(const FileMapping& fileObj, const
zen::copyFile(source, //type File implicitly means symlinks need to be dereferenced!
target,
- copyFilePermissions,
- transactionalFileCopy,
+ copyFilePermissions_,
+ transactionalFileCopy_,
&callback,
&newAttr); //throw FileError, ErrorFileLocked
@@ -2280,7 +2288,7 @@ void SynchronizeFolderPair::copyFileUpdatingTo(const FileMapping& fileObj, const
//#################### Verification #############################
- if (verifyCopiedFiles)
+ if (verifyCopiedFiles_)
{
zen::ScopeGuard guardTarget = zen::makeGuard([&] { removeFile(target); }); //delete target if verification fails
zen::ScopeGuard guardStatistics = zen::makeGuard([&]
bgstack15