Index: src/ch/MainWnd.cpp =================================================================== diff -u -N -rbe5d5dfa17e79a1db8e64ad2d2ed5faea30399cb -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/ch/MainWnd.cpp (.../MainWnd.cpp) (revision be5d5dfa17e79a1db8e64ad2d2ed5faea30399cb) +++ src/ch/MainWnd.cpp (.../MainWnd.cpp) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -181,7 +181,7 @@ CString strPath; GetApp().GetProgramDataPath(strPath); strPath += _T("\\Tasks\\"); - m_tasks.SetTasksDir(strPath); + m_tasks.SetTasksDir(chcore::PathFromString(strPath)); // load tasks m_tasks.LoadDataProgress(); @@ -499,14 +499,16 @@ { if(rCommandLine.HasTaskDefinitionPath()) { - std::vector vTaskPaths; + chcore::TPathContainer vTaskPaths; rCommandLine.GetTaskDefinitionPaths(vTaskPaths); const size_t stBufferSize = 4096; boost::shared_array szBuffer(new wchar_t[stBufferSize]); - BOOST_FOREACH(const CString& strPath, vTaskPaths) + for(size_t stIndex = 0; stIndex < vTaskPaths.GetCount(); ++stIndex) { + const chcore::TSmartPath& strPath = vTaskPaths.GetAt(stIndex); + bool bImported = false; try @@ -531,13 +533,13 @@ { ictranslate::CFormat fmt; fmt.SetFormat(_T("Error encountered while importing task from path '%path'. Error: %err.")); - fmt.SetParam(_T("%path"), strPath); + fmt.SetParam(_T("%path"), strPath.ToString()); fmt.SetParam(_T("%error"), szBuffer.get()); LOG_ERROR(fmt); fmt.SetFormat(GetResManager().LoadString(IDS_TASK_IMPORT_FAILED)); - fmt.SetParam(_T("%path"), strPath); + fmt.SetParam(_T("%path"), strPath.ToString()); AfxMessageBox(fmt, MB_OK | MB_ICONERROR); } } Index: src/ch/StatusDlg.cpp =================================================================== diff -u -N -r6dc950d4d76107421ff6eb62069b70f20bcc450e -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/ch/StatusDlg.cpp (.../StatusDlg.cpp) (revision 6dc950d4d76107421ff6eb62069b70f20bcc450e) +++ src/ch/StatusDlg.cpp (.../StatusDlg.cpp) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -783,12 +783,12 @@ if (!spTask) return; - unsigned long lResult = (unsigned long)(ShellExecute(this->m_hWnd, _T("open"), _T("notepad.exe"), spTask->GetRelatedPath(CTask::ePathType_TaskLogFile), NULL, SW_SHOWNORMAL)); + unsigned long lResult = (unsigned long)(ShellExecute(this->m_hWnd, _T("open"), _T("notepad.exe"), spTask->GetRelatedPath(CTask::ePathType_TaskLogFile).ToString(), NULL, SW_SHOWNORMAL)); if(lResult < 32) { ictranslate::CFormat fmt(GetResManager().LoadString(IDS_SHELLEXECUTEERROR_STRING)); fmt.SetParam(_t("%errno"), lResult); - fmt.SetParam(_t("%path"), spTask->GetRelatedPath(CTask::ePathType_TaskLogFile)); + fmt.SetParam(_t("%path"), spTask->GetRelatedPath(CTask::ePathType_TaskLogFile).ToString()); AfxMessageBox(fmt); } } Index: src/ch/TCommandLineParser.cpp =================================================================== diff -u -N -r8dd3566d66a35a662872eaaa45eef5049e71c3dc -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/ch/TCommandLineParser.cpp (.../TCommandLineParser.cpp) (revision 8dd3566d66a35a662872eaaa45eef5049e71c3dc) +++ src/ch/TCommandLineParser.cpp (.../TCommandLineParser.cpp) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -23,6 +23,7 @@ #include "stdafx.h" #include "TCommandLineParser.h" #include +#include "../libchcore/TPath.h" TCommandLineParser::TCommandLineParser() { @@ -59,14 +60,17 @@ return m_mapVariables.count("ImportTaskDefinition") > 0; } -void TCommandLineParser::GetTaskDefinitionPaths(std::vector& vPaths) const +void TCommandLineParser::GetTaskDefinitionPaths(chcore::TPathContainer& vPaths) const { - vPaths.clear(); + vPaths.Clear(); std::vector vValues; if(HasTaskDefinitionPath()) { vValues = m_mapVariables["ImportTaskDefinition"].as >(); - std::transform(vValues.begin(), vValues.end(), std::back_inserter(vPaths), boost::bind(&std::wstring::c_str, _1)); + BOOST_FOREACH(std::wstring& strPath, vValues) + { + vPaths.Add(chcore::PathFromString(strPath.c_str())); + } } } Index: src/ch/TCommandLineParser.h =================================================================== diff -u -N -r8dd3566d66a35a662872eaaa45eef5049e71c3dc -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/ch/TCommandLineParser.h (.../TCommandLineParser.h) (revision 8dd3566d66a35a662872eaaa45eef5049e71c3dc) +++ src/ch/TCommandLineParser.h (.../TCommandLineParser.h) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -25,6 +25,8 @@ #include +namespace chcore { class TPathContainer; } + class TCommandLineParser { public: @@ -36,7 +38,7 @@ bool HasCommandLineParams() const; bool HasTaskDefinitionPath() const; - void GetTaskDefinitionPaths(std::vector& vPaths) const; + void GetTaskDefinitionPaths(chcore::TPathContainer& vPaths) const; private: boost::program_options::variables_map m_mapVariables; Index: src/ch/task.cpp =================================================================== diff -u -N -r633a533cb6e741d44fe28aa56339e1d2709b1b27 -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/ch/task.cpp (.../task.cpp) (revision 633a533cb6e741d44fe28aa56339e1d2709b1b27) +++ src/ch/task.cpp (.../task.cpp) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -137,13 +137,13 @@ m_localStats.SetProcessedSize(m_files.CalculatePartialSize(m_tTaskBasicProgressInfo.GetCurrentIndex())); } -void CTask::Load(const CString& strPath) +void CTask::Load(const chcore::TSmartPath& strPath) { boost::unique_lock lock(m_lock); //////////////////////////////// // First load task description - m_tTaskDefinition.Load((PCTSTR)strPath); + m_tTaskDefinition.Load(strPath); m_strFilePath = strPath; // update members according to the task definition @@ -153,8 +153,8 @@ //////////////////////////////// // now rarely changing task progress data - CString strRarelyChangingPath = GetRelatedPathNL(ePathType_TaskRarelyChangingState); - std::ifstream ifs(strRarelyChangingPath, ios_base::in | ios_base::binary); + chcore::TSmartPath pathRarelyChangingPath = GetRelatedPathNL(ePathType_TaskRarelyChangingState); + std::ifstream ifs(pathRarelyChangingPath.ToString(), ios_base::in | ios_base::binary); boost::archive::binary_iarchive ar(ifs); m_arrSourcePathsInfo.Load(ar, 0, true); @@ -164,8 +164,8 @@ /////////////////////////////////// // and often changing data - CString strOftenChangingPath = GetRelatedPathNL(ePathType_TaskOftenChangingState); - std::ifstream ifs2(strOftenChangingPath, ios_base::in | ios_base::binary); + chcore::TSmartPath pathOftenChangingPath = GetRelatedPathNL(ePathType_TaskOftenChangingState); + std::ifstream ifs2(pathOftenChangingPath.ToString(), ios_base::in | ios_base::binary); boost::archive::binary_iarchive ar2(ifs2); ar2 >> m_tTaskBasicProgressInfo; @@ -207,16 +207,16 @@ if(m_strFilePath.IsEmpty()) { boost::upgrade_to_unique_lock upgraded_lock(lock); - m_strFilePath = m_strTaskDirectory + m_tTaskDefinition.GetTaskUniqueID() + _T(".cht"); + m_strFilePath = m_strTaskDirectory + chcore::PathFromWString(m_tTaskDefinition.GetTaskUniqueID() + _T(".cht")); } // store task definition only if changed - m_tTaskDefinition.Store((PCTSTR)GetRelatedPathNL(ePathType_TaskDefinition), true); + m_tTaskDefinition.Store(GetRelatedPathNL(ePathType_TaskDefinition), true); // rarely changing data if(m_bRareStateModified) { - std::ofstream ofs(GetRelatedPathNL(ePathType_TaskRarelyChangingState), ios_base::out | ios_base::binary); + std::ofstream ofs(GetRelatedPathNL(ePathType_TaskRarelyChangingState).ToString(), ios_base::out | ios_base::binary); boost::archive::binary_oarchive ar(ofs); m_arrSourcePathsInfo.Store(ar, 0, true); @@ -225,7 +225,7 @@ if(m_bOftenStateModified) { - std::ofstream ofs(GetRelatedPathNL(ePathType_TaskOftenChangingState), ios_base::out | ios_base::binary); + std::ofstream ofs(GetRelatedPathNL(ePathType_TaskOftenChangingState).ToString(), ios_base::out | ios_base::binary); boost::archive::binary_oarchive ar(ofs); ar << m_tTaskBasicProgressInfo; @@ -433,21 +433,21 @@ void CTask::DeleteProgress() { - std::vector vFilesToRemove; + chcore::TPathContainer vFilesToRemove; // separate scope for shared locking { boost::shared_lock lock(m_lock); - vFilesToRemove.push_back(GetRelatedPath(ePathType_TaskDefinition)); - vFilesToRemove.push_back(GetRelatedPath(ePathType_TaskRarelyChangingState)); - vFilesToRemove.push_back(GetRelatedPath(ePathType_TaskOftenChangingState)); - vFilesToRemove.push_back(GetRelatedPath(ePathType_TaskLogFile)); + vFilesToRemove.Add(GetRelatedPath(ePathType_TaskDefinition)); + vFilesToRemove.Add(GetRelatedPath(ePathType_TaskRarelyChangingState)); + vFilesToRemove.Add(GetRelatedPath(ePathType_TaskOftenChangingState)); + vFilesToRemove.Add(GetRelatedPath(ePathType_TaskLogFile)); } - BOOST_FOREACH(const CString& strFile, vFilesToRemove) + for(size_t stIndex = 0; stIndex < vFilesToRemove.GetCount(); ++stIndex) { - DeleteFile(strFile); + DeleteFile(vFilesToRemove.GetAt(stIndex).ToString()); } } @@ -484,25 +484,25 @@ return (*pullNeeded <= *pullAvailable); } -void CTask::SetTaskDirectory(const CString& strDir) +void CTask::SetTaskDirectory(const chcore::TSmartPath& strDir) { boost::unique_lock lock(m_lock); m_strTaskDirectory = strDir; } -CString CTask::GetTaskDirectory() const +chcore::TSmartPath CTask::GetTaskDirectory() const { boost::shared_lock lock(m_lock); return m_strTaskDirectory; } -void CTask::SetTaskFilePath(const CString& strFilePath) +void CTask::SetTaskFilePath(const chcore::TSmartPath& strFilePath) { boost::unique_lock lock(m_lock); m_strFilePath = strFilePath; } -CString CTask::GetTaskFilePath() const +chcore::TSmartPath CTask::GetTaskFilePath() const { boost::shared_lock lock(m_lock); return m_strFilePath; @@ -658,9 +658,9 @@ TSubTaskBase::ESubOperationResult eResult = TSubTaskBase::eSubResult_Continue; // initialize log file - CString strPath = GetRelatedPath(ePathType_TaskLogFile); + chcore::TSmartPath pathLogFile = GetRelatedPath(ePathType_TaskLogFile); - m_log.init(strPath, 262144, icpf::log_file::level_debug, false, false); + m_log.init(pathLogFile.ToString(), 262144, icpf::log_file::level_debug, false, false); // start operation OnBeginOperation(); @@ -874,37 +874,37 @@ m_workerThread.SignalThreadToStop(); } -CString CTask::GetRelatedPath(EPathType ePathType) +chcore::TSmartPath CTask::GetRelatedPath(EPathType ePathType) { boost::shared_lock lock(m_lock); return GetRelatedPathNL(ePathType); } -CString CTask::GetRelatedPathNL(EPathType ePathType) +chcore::TSmartPath CTask::GetRelatedPathNL(EPathType ePathType) { BOOST_ASSERT(!m_strTaskDirectory.IsEmpty() || !m_strFilePath.IsEmpty()); if(m_strTaskDirectory.IsEmpty() && m_strFilePath.IsEmpty()) THROW(_t("Missing task path."), 0, 0, 0); // in all cases we would like to have task definition path defined - CString strFilePath = m_strFilePath; + chcore::TSmartPath strFilePath = m_strFilePath; if(strFilePath.IsEmpty()) - strFilePath = m_strTaskDirectory + m_tTaskDefinition.GetTaskUniqueID() + _T(".cht"); + strFilePath = m_strTaskDirectory + chcore::PathFromWString(m_tTaskDefinition.GetTaskUniqueID() + _T(".cht")); switch(ePathType) { case ePathType_TaskDefinition: return strFilePath; case ePathType_TaskRarelyChangingState: - return strFilePath + _T(".rstate"); + return strFilePath.AppendCopy(chcore::PathFromString(_T(".rstate")), false); case ePathType_TaskOftenChangingState: - return strFilePath + _T(".ostate"); + return strFilePath.AppendCopy(chcore::PathFromString(_T(".ostate")), false); case ePathType_TaskLogFile: - return strFilePath + _T(".log"); + return strFilePath.AppendCopy(chcore::PathFromString(_T(".log")), false); default: THROW(_t("Unhandled case"), 0, 0, 0); @@ -956,11 +956,11 @@ return spTask; } -CTaskPtr CTaskArray::ImportTask(const CString& strTaskPath) +CTaskPtr CTaskArray::ImportTask(const chcore::TSmartPath& strTaskPath) { // load task definition from the new location chcore::TTaskDefinition tTaskDefinition; - tTaskDefinition.Load((PCTSTR)strTaskPath); + tTaskDefinition.Load(strTaskPath); return CreateTask(tTaskDefinition); } @@ -1029,7 +1029,7 @@ boost::unique_lock lock(m_lock); // here we know load succeeded - spNewTask->SetTaskDirectory(m_strTasksDir.c_str()); + spNewTask->SetTaskDirectory(m_pathTasksDir); m_vTasks.push_back(spNewTask); @@ -1164,27 +1164,29 @@ { CFileFind finder; CTaskPtr spTask; - CString strPath; + chcore::TSmartPath pathFound; // find all CH Task files - BOOL bWorking = finder.FindFile(CString(m_strTasksDir.c_str()) + _T("*.cht")); + chcore::TSmartPath pathToFind = m_pathTasksDir + chcore::PathFromString(_T("*.cht")); + BOOL bWorking = finder.FindFile(pathToFind.ToString()); while(bWorking) { bWorking = finder.FindNextFile(); + pathFound = chcore::PathFromString(finder.GetFilePath()); // load data spTask = CreateEmptyTask(); try { - spTask->Load(finder.GetFilePath()); + spTask->Load(pathFound); // add read task to array Add(spTask); } catch(std::exception& e) { CString strFmt; - strFmt.Format(_T("Cannot load task data: %s (reason: %S)"), (PCTSTR)strPath, e.what()); + strFmt.Format(_T("Cannot load task data: %s (reason: %S)"), pathFound.ToString(), e.what()); LOG_ERROR(strFmt); } catch(icpf::exception& e) @@ -1194,7 +1196,7 @@ strMsg.ReleaseBuffer(); CString strFmt; - strFmt.Format(_T("Cannot load task data: %s (reason: %s)"), (PCTSTR)strPath, (PCTSTR)strMsg); + strFmt.Format(_T("Cannot load task data: %s (reason: %s)"), pathFound.ToString(), (PCTSTR)strMsg); LOG_ERROR(strFmt); } } @@ -1296,10 +1298,10 @@ return bFlag; } -void CTaskArray::SetTasksDir(const tchar_t* pszPath) +void CTaskArray::SetTasksDir(const chcore::TSmartPath& pathDir) { boost::unique_lock lock(m_lock); - m_strTasksDir = pszPath; + m_pathTasksDir = pathDir; } void CTaskArray::StopAllTasksNL() Index: src/ch/task.h =================================================================== diff -u -N -r633a533cb6e741d44fe28aa56339e1d2709b1b27 -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/ch/task.h (.../task.h) (revision 633a533cb6e741d44fe28aa56339e1d2709b1b27) +++ src/ch/task.h (.../task.h) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -122,7 +122,7 @@ // thread void SetPriority(int nPriority); - void Load(const CString& strPath); + void Load(const chcore::TSmartPath& strPath); void Store(); void BeginProcessing(); @@ -136,18 +136,18 @@ void GetSnapshot(TASK_DISPLAY_DATA *pData); void GetMiniSnapshot(TASK_MINI_DISPLAY_DATA *pData); - void SetTaskDirectory(const CString& strDir); - CString GetTaskDirectory() const; + void SetTaskDirectory(const chcore::TSmartPath& strDir); + chcore::TSmartPath GetTaskDirectory() const; - void SetTaskFilePath(const CString& strPath); - CString GetTaskFilePath() const; + void SetTaskFilePath(const chcore::TSmartPath& strPath); + chcore::TSmartPath GetTaskFilePath() const; void SetForceFlag(bool bFlag = true); bool GetForceFlag(); size_t GetSessionUniqueID() const { return m_stSessionUniqueID; } - CString GetRelatedPath(EPathType ePathType); + chcore::TSmartPath GetRelatedPath(EPathType ePathType); protected: CTask(chcore::IFeedbackHandler* piFeedbackHandler, size_t stSessionUniqueID); @@ -204,7 +204,7 @@ void KillThread(); void RequestStopThread(); - CString GetRelatedPathNL(EPathType ePathType); + chcore::TSmartPath GetRelatedPathNL(EPathType ePathType); static void OnCfgOptionChanged(const chcore::TStringSet& rsetChanges, void* pParam); @@ -234,8 +234,8 @@ bool m_bForce; // if the continuation of tasks should be independent of max concurrently running task limit bool m_bContinue; // allows task to continue - CString m_strTaskDirectory; // base path at which the files will be stored - CString m_strFilePath; // exact filename with path to the task definition file + chcore::TSmartPath m_strTaskDirectory; // base path at which the files will be stored + chcore::TSmartPath m_strFilePath; // exact filename with path to the task definition file bool m_bRareStateModified; // rarely changing state has been modified bool m_bOftenStateModified; // rarely changing state has been modified @@ -271,7 +271,7 @@ void Create(chcore::IFeedbackHandlerFactory* piFeedbackHandlerFactory); CTaskPtr CreateTask(const chcore::TTaskDefinition& tTaskDefinition); - CTaskPtr ImportTask(const CString& strTaskPath); + CTaskPtr ImportTask(const chcore::TSmartPath& strTaskPath); size_t GetSize() const; @@ -304,15 +304,15 @@ bool AreAllFinished(); - void SetTasksDir(const tchar_t* pszPath); + void SetTasksDir(const chcore::TSmartPath& pathDir); protected: void StopAllTasksNL(); CTaskPtr CreateEmptyTask(); public: - tstring_t m_strTasksDir; + chcore::TSmartPath m_pathTasksDir; mutable boost::shared_mutex m_lock; Index: src/libchcore/TPath.cpp =================================================================== diff -u -N -r633a533cb6e741d44fe28aa56339e1d2709b1b27 -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/libchcore/TPath.cpp (.../TPath.cpp) (revision 633a533cb6e741d44fe28aa56339e1d2709b1b27) +++ src/libchcore/TPath.cpp (.../TPath.cpp) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -125,7 +125,7 @@ /// @brief Constructs an empty path. // ============================================================================ TSmartPath::TSmartPath() : -m_pPath(NULL) + m_pPath(NULL) { } @@ -137,7 +137,7 @@ /// @param[in] spPath - reference to another path object. // ============================================================================ TSmartPath::TSmartPath(const TSmartPath& spPath) : -m_pPath(spPath.m_pPath) + m_pPath(spPath.m_pPath) { if(m_pPath) m_pPath->AddRef(); @@ -170,6 +170,52 @@ } } + +TSmartPath TSmartPath::AppendCopy(const TSmartPath& pathToAppend, bool bEnsurePathSeparatorExists) const +{ + TSmartPath pathNew(*this); + pathNew.Append(pathToAppend, bEnsurePathSeparatorExists); + + return pathNew; +} + +TSmartPath& TSmartPath::Append(const TSmartPath& pathToAppend, bool bEnsurePathSeparatorExists) +{ + // if there is no path inside rPath, then there is no point in doing anything + if(pathToAppend.m_pPath && pathToAppend.m_pPath->m_strPath.GetLength() > 0) + { + // if this path is empty, then optimize by just assigning the input path to this one + if(!m_pPath || m_pPath->m_strPath.GetLength() == 0) + *this = pathToAppend; + else + { + // both paths are not empty - do regular concatenation + PrepareToWrite(); + + if(bEnsurePathSeparatorExists) + { + // detect separators + bool bThisEndsWithSeparator = EndsWithSeparator(); + bool bInStartsWithSeparator = pathToAppend.StartsWithSeparator(); + + if(!bThisEndsWithSeparator && !bInStartsWithSeparator) + m_pPath->m_strPath += _T("\\") + pathToAppend.m_pPath->m_strPath; + else if(bThisEndsWithSeparator ^ bInStartsWithSeparator) + m_pPath->m_strPath += pathToAppend.m_pPath->m_strPath; + else + { + m_pPath->m_strPath.DeleteChar(m_pPath->m_strPath.GetLength() - 1); + m_pPath->m_strPath += pathToAppend.m_pPath->m_strPath; + } + } + else + m_pPath->m_strPath += pathToAppend.m_pPath->m_strPath; + } + } + + return *this; +} + // ============================================================================ /// TSmartPath::operator= /// @date 2009/11/29 @@ -262,40 +308,7 @@ // ============================================================================ TSmartPath TSmartPath::operator+(const TSmartPath& rPath) const { - if(rPath.m_pPath && rPath.m_pPath->m_strPath.GetLength() > 0) - { - // if this path is empty, then return the input one - if(!m_pPath || rPath.m_pPath->m_strPath.GetLength() == 0) - return rPath; - else - { - TSmartPath spNewPath(*this); - - // both paths contains something to be concatenated - spNewPath.PrepareToWrite(); - - // detect separators - bool bThisEndsWithSeparator = EndsWithSeparator(); - bool bInStartsWithSeparator = rPath.StartsWithSeparator(); - - if(!bThisEndsWithSeparator && !bInStartsWithSeparator) - spNewPath.m_pPath->m_strPath += _T("\\") + rPath.m_pPath->m_strPath; - else if(bThisEndsWithSeparator ^ bInStartsWithSeparator) - spNewPath.m_pPath->m_strPath += rPath.m_pPath->m_strPath; - else - { - spNewPath.m_pPath->m_strPath.DeleteChar(m_pPath->m_strPath.GetLength() - 1); - spNewPath.m_pPath->m_strPath += rPath.m_pPath->m_strPath; - } - - return spNewPath; - } - } - else - { - // input path is empty, so return this path, whatever this is - return *this; - } + return AppendCopy(rPath, true); } // ============================================================================ @@ -308,34 +321,7 @@ // ============================================================================ TSmartPath& TSmartPath::operator+=(const TSmartPath& rPath) { - // if there is no path inside rPath, then there is no point in doing anything - if(rPath.m_pPath && rPath.m_pPath->m_strPath.GetLength() > 0) - { - // if this path is empty, then optimize by just assigning the input path to this one - if(!m_pPath || m_pPath->m_strPath.GetLength() == 0) - *this = rPath; - else - { - // both paths are not empty - do regular concatenation - PrepareToWrite(); - - // detect separators - bool bThisEndsWithSeparator = EndsWithSeparator(); - bool bInStartsWithSeparator = rPath.StartsWithSeparator(); - - if(!bThisEndsWithSeparator && !bInStartsWithSeparator) - m_pPath->m_strPath += _T("\\") + rPath.m_pPath->m_strPath; - else if(bThisEndsWithSeparator ^ bInStartsWithSeparator) - m_pPath->m_strPath += rPath.m_pPath->m_strPath; - else - { - m_pPath->m_strPath.DeleteChar(m_pPath->m_strPath.GetLength() - 1); - m_pPath->m_strPath += rPath.m_pPath->m_strPath; - } - } - } - - return *this; + return Append(rPath, true); } // ============================================================================ Index: src/libchcore/TPath.h =================================================================== diff -u -N -r633a533cb6e741d44fe28aa56339e1d2709b1b27 -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/libchcore/TPath.h (.../TPath.h) (revision 633a533cb6e741d44fe28aa56339e1d2709b1b27) +++ src/libchcore/TPath.h (.../TPath.h) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -83,6 +83,9 @@ // other operations void Clear() throw(); + TSmartPath AppendCopy(const TSmartPath& pathToAppend, bool bEnsurePathSeparatorExists = true) const; + TSmartPath& Append(const TSmartPath& pathToAppend, bool bEnsurePathSeparatorExists = true); + void SplitPath(std::vector& vComponents) const; bool Compare(const TSmartPath& rPath, bool bCaseSensitive = DefaultCaseSensitivity) const; Index: src/libchcore/TTaskDefinition.cpp =================================================================== diff -u -N -rbe5d5dfa17e79a1db8e64ad2d2ed5faea30399cb -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/libchcore/TTaskDefinition.cpp (.../TTaskDefinition.cpp) (revision be5d5dfa17e79a1db8e64ad2d2ed5faea30399cb) +++ src/libchcore/TTaskDefinition.cpp (.../TTaskDefinition.cpp) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -161,11 +161,11 @@ } // Serialization -void TTaskDefinition::Load(const std::wstring& strPath) +void TTaskDefinition::Load(const TSmartPath& strPath) { // read everything chcore::TConfig tTaskInfo; - tTaskInfo.Read(strPath.c_str()); + tTaskInfo.Read(strPath.ToString()); // clear everything m_strTaskUniqueID.Clear(); @@ -224,13 +224,13 @@ tTaskInfo.ExtractSubConfig(_T("TaskDefinition.TaskSettings"), m_tConfiguration); } -void TTaskDefinition::Store(const std::wstring& strPath, bool bOnlyIfModified) +void TTaskDefinition::Store(const TSmartPath& strPath, bool bOnlyIfModified) { if(!bOnlyIfModified || m_bModified || m_tConfiguration.IsModified()) { // read everything chcore::TConfig tTaskInfo; - tTaskInfo.SetFilePath(strPath.c_str()); + tTaskInfo.SetFilePath(strPath.ToString()); // get information from config file // task unique id - use if provided, generate otherwise Index: src/libchcore/TTaskDefinition.h =================================================================== diff -u -N -rbe5d5dfa17e79a1db8e64ad2d2ed5faea30399cb -r0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f --- src/libchcore/TTaskDefinition.h (.../TTaskDefinition.h) (revision be5d5dfa17e79a1db8e64ad2d2ed5faea30399cb) +++ src/libchcore/TTaskDefinition.h (.../TTaskDefinition.h) (revision 0cd863a6e51b221c4f7bf6e7b83ddfc43a5d433f) @@ -63,13 +63,13 @@ const TOperationPlan& GetOperationPlan() const; // Task configuration - void SetConfiguration(const chcore::TConfig& rConfig); - chcore::TConfig& GetConfiguration(); - const chcore::TConfig& GetConfiguration() const; + void SetConfiguration(const TConfig& rConfig); + TConfig& GetConfiguration(); + const TConfig& GetConfiguration() const; // Serialization - void Load(const std::wstring& strPath); - void Store(const std::wstring& strPath, bool bOnlyIfModified = false); + void Load(const TSmartPath& strPath); + void Store(const TSmartPath& strPath, bool bOnlyIfModified = false); void StoreInString(TString& strInput); void LoadFromString(const TString& strInput);