Index: src/ch/ClipboardMonitor.cpp =================================================================== diff -u -r9352ed0c4fe447a36bc728640c307be6d41455fd -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/ClipboardMonitor.cpp (.../ClipboardMonitor.cpp) (revision 9352ed0c4fe447a36bc728640c307be6d41455fd) +++ src/ch/ClipboardMonitor.cpp (.../ClipboardMonitor.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -96,7 +96,7 @@ // bufor TCHAR path[_MAX_PATH]; // UINT i; // counter - CTask *pTask; // ptr to a task + CTaskPtr spTask; // ptr to a task CClipboardEntryPtr spEntry; // register clipboard format @@ -116,14 +116,14 @@ UINT nCount=DragQueryFile(static_cast(handle), 0xffffffff, NULL, 0); - pTask = pData->m_pTasks->CreateTask(); + spTask = pData->m_pTasks->CreateTask(); for (UINT i=0;i(handle), i, path, _MAX_PATH); spEntry.reset(new CClipboardEntry); spEntry->SetPath(path); - pTask->AddClipboardData(spEntry); + spTask->AddClipboardData(spEntry); } if (IsClipboardFormatAvailable(nFormat)) @@ -133,14 +133,14 @@ DWORD dwData=((DWORD*)addr)[0]; if (dwData & DROPEFFECT_COPY) - pTask->SetStatus(ST_COPY, ST_OPERATION_MASK); // copy + spTask->SetStatus(ST_COPY, ST_OPERATION_MASK); // copy else if (dwData & DROPEFFECT_MOVE) - pTask->SetStatus(ST_MOVE, ST_OPERATION_MASK); // move + spTask->SetStatus(ST_MOVE, ST_OPERATION_MASK); // move GlobalUnlock(handle); } else - pTask->SetStatus(ST_COPY, ST_OPERATION_MASK); // default - copy + spTask->SetStatus(ST_COPY, ST_OPERATION_MASK); // default - copy EmptyClipboard(); CloseClipboard(); @@ -153,8 +153,8 @@ bs.m_uiCDSize=(UINT)rConfig.get_signed_num(PP_BFCD); bs.m_uiLANSize=(UINT)rConfig.get_signed_num(PP_BFLAN); - pTask->SetBufferSizes(&bs); - pTask->SetPriority(boost::numeric_cast(rConfig.get_signed_num(PP_CMDEFAULTPRIORITY))); + spTask->SetBufferSizes(&bs); + spTask->SetPriority(boost::numeric_cast(rConfig.get_signed_num(PP_CMDEFAULTPRIORITY))); // get dest folder CFolderDialog dlg; @@ -184,7 +184,7 @@ dlg.m_bdData.strInitialDir=(dlg.m_bdData.cvRecent.size() > 0) ? dlg.m_bdData.cvRecent.at(0) : _T(""); - int iStatus=pTask->GetStatus(ST_OPERATION_MASK); + int iStatus=spTask->GetStatus(ST_OPERATION_MASK); if (iStatus == ST_COPY) dlg.m_bdData.strCaption=GetResManager().LoadString(IDS_TITLECOPY_STRING); else if (iStatus == ST_MOVE) @@ -194,11 +194,11 @@ dlg.m_bdData.strText=GetResManager().LoadString(IDS_MAINBROWSETEXT_STRING); // set count of data to display - size_t stClipboardSize = pTask->GetClipboardDataSize(); + size_t stClipboardSize = spTask->GetClipboardDataSize(); size_t stEntries = (stClipboardSize > 3) ? 2 : stClipboardSize; for(size_t i = 0; i < stEntries; i++) { - dlg.m_bdData.strText += pTask->GetClipboardData(i)->GetPath() + _T("\n"); + dlg.m_bdData.strText += spTask->GetClipboardData(i)->GetPath() + _T("\n"); } // add ... @@ -228,30 +228,30 @@ rConfig.set_bool(PP_FDIGNORESHELLDIALOGS, dlg.m_bdData.bIgnoreDialogs); rConfig.write(NULL); - if ( iResult != IDOK ) - delete pTask; + if(iResult != IDOK) + spTask.reset(); else { // get dest path CString strData; dlg.GetPath(strData); - pTask->SetDestPath(strData); + spTask->SetDestPath(strData); // get the relationship between src and dst paths - for (size_t stIndex = 0; stIndex < pTask->GetClipboard()->GetSize(); ++stIndex) + for (size_t stIndex = 0; stIndex < spTask->GetClipboard()->GetSize(); ++stIndex) { - pTask->GetClipboard()->GetAt(stIndex)->CalcBufferIndex(pTask->GetDestPath()); + spTask->GetClipboard()->GetAt(stIndex)->CalcBufferIndex(spTask->GetDestPath()); } // add task to a list of tasks and start - pData->m_pTasks->Add(pTask); + pData->m_pTasks->Add(spTask); - // write pTask to a file - pTask->Store(true); - pTask->Store(false); + // write spTask to a file + spTask->Store(true); + spTask->Store(false); // start processing - pTask->BeginProcessing(); + spTask->BeginProcessing(); } } Index: src/ch/MainWnd.cpp =================================================================== diff -u -r9352ed0c4fe447a36bc728640c307be6d41455fd -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/MainWnd.cpp (.../MainWnd.cpp) (revision 9352ed0c4fe447a36bc728640c307be6d41455fd) +++ src/ch/MainWnd.cpp (.../MainWnd.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -333,10 +333,10 @@ ///////////////////////////////////////////////////////////////////////////// // CMainWnd/CTrayIcon menu message handlers -void CMainWnd::ShowStatusWindow(const CTask *pSelect) +void CMainWnd::ShowStatusWindow(const CTaskPtr& spSelect) { m_pdlgStatus=new CStatusDlg(&m_tasks, this); // self deleting - m_pdlgStatus->m_pInitialSelection=pSelect; + m_pdlgStatus->m_spInitialSelection = spSelect; m_pdlgStatus->m_bLockInstance=true; m_pdlgStatus->m_bAutoDelete=true; m_pdlgStatus->Create(); @@ -402,19 +402,19 @@ case 8743: { // wait state handling section - CTask* pTask; + CTaskPtr spTask; if (GetConfig().get_signed_num(PP_CMLIMITMAXOPERATIONS) == 0 || m_tasks.GetOperationsPending() < (UINT)GetConfig().get_signed_num(PP_CMLIMITMAXOPERATIONS)) { for(size_t stIndex = 0; stIndex < m_tasks.GetSize(); ++stIndex) { - pTask = m_tasks.GetAt(stIndex); + spTask = m_tasks.GetAt(stIndex); // turn on some thread - find something with wait state - if (pTask->GetStatus(ST_WAITING_MASK) & ST_WAITING && (GetConfig().get_signed_num(PP_CMLIMITMAXOPERATIONS) == 0 || m_tasks.GetOperationsPending() < (UINT)GetConfig().get_signed_num(PP_CMLIMITMAXOPERATIONS))) + if(spTask->GetStatus(ST_WAITING_MASK) & ST_WAITING && (GetConfig().get_signed_num(PP_CMLIMITMAXOPERATIONS) == 0 || m_tasks.GetOperationsPending() < (UINT)GetConfig().get_signed_num(PP_CMLIMITMAXOPERATIONS))) { TRACE("Enabling task %ld\n", stIndex); - pTask->SetContinueFlag(true); - pTask->IncreaseOperationsPending(); - pTask->SetStatus(0, ST_WAITING); // turn off wait state + spTask->SetContinueFlag(true); + spTask->IncreaseOperationsPending(); + spTask->SetStatus(0, ST_WAITING); // turn off wait state } } } @@ -541,38 +541,38 @@ } // create new task - CTask *pTask = m_tasks.CreateTask(); - pTask->SetDestPath(strDstPath); + CTaskPtr spTask = m_tasks.CreateTask(); + spTask->SetDestPath(strDstPath); CClipboardEntryPtr spEntry; // files for (int i=0;iSetPath(astrFiles.GetAt(i)); - spEntry->CalcBufferIndex(pTask->GetDestPath()); - pTask->AddClipboardData(spEntry); + spEntry->CalcBufferIndex(spTask->GetDestPath()); + spTask->AddClipboardData(spEntry); } - pTask->SetStatus(bMove ? ST_MOVE : ST_COPY, ST_OPERATION_MASK); + spTask->SetStatus(bMove ? ST_MOVE : ST_COPY, ST_OPERATION_MASK); // special status - pTask->SetStatus((bOnlyCreate ? ST_IGNORE_CONTENT : 0) | (bIgnoreDirs ? ST_IGNORE_DIRS : 0) | (bForceDirectories ? ST_FORCE_DIRS : 0), ST_SPECIAL_MASK); + spTask->SetStatus((bOnlyCreate ? ST_IGNORE_CONTENT : 0) | (bIgnoreDirs ? ST_IGNORE_DIRS : 0) | (bForceDirectories ? ST_FORCE_DIRS : 0), ST_SPECIAL_MASK); // set some stuff related with task - pTask->SetBufferSizes(&bsSizes); - pTask->SetPriority(iPriority); - pTask->SetFilters(&ffFilters); - pTask->SetCopies(ucCopies); + spTask->SetBufferSizes(&bsSizes); + spTask->SetPriority(iPriority); + spTask->SetFilters(&ffFilters); + spTask->SetCopies(ucCopies); - m_tasks.Add(pTask); + m_tasks.Add(spTask); // save state of a task - pTask->Store(true); - pTask->Store(false); + spTask->Store(true); + spTask->Store(false); // add to task list and start processing - pTask->BeginProcessing(); + spTask->BeginProcessing(); return CWnd::OnCopyData(pWnd, pCopyDataStruct); } @@ -626,35 +626,35 @@ } // new task - CTask *pTask = m_tasks.CreateTask(); - pTask->SetDestPath(dlg.m_ccData.m_strDestPath); + CTaskPtr spTask = m_tasks.CreateTask(); + spTask->SetDestPath(dlg.m_ccData.m_strDestPath); CClipboardEntryPtr spEntry; for (int i=0;iSetPath(dlg.m_ccData.m_astrPaths.GetAt(i)); - spEntry->CalcBufferIndex(pTask->GetDestPath()); - pTask->AddClipboardData(spEntry); + spEntry->CalcBufferIndex(spTask->GetDestPath()); + spTask->AddClipboardData(spEntry); } - pTask->SetStatus((dlg.m_ccData.m_iOperation == 1) ? ST_MOVE : ST_COPY, ST_OPERATION_MASK); + spTask->SetStatus((dlg.m_ccData.m_iOperation == 1) ? ST_MOVE : ST_COPY, ST_OPERATION_MASK); // special status - pTask->SetStatus((dlg.m_ccData.m_bCreateStructure ? ST_IGNORE_CONTENT : 0) | (dlg.m_ccData.m_bIgnoreFolders ? ST_IGNORE_DIRS : 0) + spTask->SetStatus((dlg.m_ccData.m_bCreateStructure ? ST_IGNORE_CONTENT : 0) | (dlg.m_ccData.m_bIgnoreFolders ? ST_IGNORE_DIRS : 0) | (dlg.m_ccData.m_bForceDirectories ? ST_FORCE_DIRS : 0), ST_SPECIAL_MASK); - pTask->SetBufferSizes(&dlg.m_ccData.m_bsSizes); - pTask->SetPriority(dlg.m_ccData.m_iPriority); - pTask->SetFilters(&dlg.m_ccData.m_afFilters); + spTask->SetBufferSizes(&dlg.m_ccData.m_bsSizes); + spTask->SetPriority(dlg.m_ccData.m_iPriority); + spTask->SetFilters(&dlg.m_ccData.m_afFilters); - m_tasks.Add(pTask); + m_tasks.Add(spTask); // save - pTask->Store(true); - pTask->Store(false); + spTask->Store(true); + spTask->Store(false); // store and start - pTask->BeginProcessing(); + spTask->BeginProcessing(); } } @@ -664,7 +664,8 @@ { case WM_MINIVIEWDBLCLK: { - ShowStatusWindow((CTask*)lParam); + CTaskPtr spTask = m_tasks.GetTaskBySessionUniqueID(lParam); + ShowStatusWindow(spTask); break; } case WM_SHOWMINIVIEW: @@ -925,31 +926,13 @@ // kill thread that monitors clipboard CClipboardMonitor::StopMonitor(); - // kill all unfinished tasks - send kill request - for(size_t stIndex = 0; stIndex < m_tasks.GetSize(); ++stIndex) - { - m_tasks.GetAt(stIndex)->SetKillFlag(); - } + m_tasks.StopAllTasks(); - // wait for finishing - for(size_t stIndex = 0; stIndex < m_tasks.GetSize(); ++stIndex) - { - while(!m_tasks.GetAt(stIndex)->GetKilledFlag()) - Sleep(10); - m_tasks.GetAt(stIndex)->CleanupAfterKill(); - } - // save m_tasks.SaveProgress(); // delete all tasks - size_t stSize = m_tasks.GetSize(); - while(stSize--) - { - delete m_tasks.GetAt(stSize); - } - - (static_cast< CArray* >(&m_tasks))->RemoveAll(); + m_tasks.RemoveAll(); } void CMainWnd::OnAppExit() Index: src/ch/MainWnd.h =================================================================== diff -u -r59c39dd19e2c42f33189ee07274f0488d54d7ed0 -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/MainWnd.h (.../MainWnd.h) (revision 59c39dd19e2c42f33189ee07274f0488d54d7ed0) +++ src/ch/MainWnd.h (.../MainWnd.h) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -66,7 +66,7 @@ protected: BOOL RegisterClass(); int ShowTrayIcon(); - void ShowStatusWindow(const CTask* pSelect=NULL); + void ShowStatusWindow(const CTaskPtr& spSelect = CTaskPtr()); void PrepareToExit(); //{{AFX_MSG(CMainWnd) afx_msg void OnPopupShowStatus(); Index: src/ch/MiniViewDlg.cpp =================================================================== diff -u -r9352ed0c4fe447a36bc728640c307be6d41455fd -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/MiniViewDlg.cpp (.../MiniViewDlg.cpp) (revision 9352ed0c4fe447a36bc728640c307be6d41455fd) +++ src/ch/MiniViewDlg.cpp (.../MiniViewDlg.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -179,16 +179,16 @@ int index=0; _PROGRESSITEM_* pItem=NULL; - if (GetConfig().get_bool(PP_MVSHOWSINGLETASKS)) + if(GetConfig().get_bool(PP_MVSHOWSINGLETASKS)) { for(size_t stIndex = 0; stIndex < m_pTasks->GetSize(); ++stIndex) { - CTask* pTask=m_pTasks->GetAt(stIndex); - pTask->GetMiniSnapshot(&dd); + CTaskPtr spTask = m_pTasks->GetAt(stIndex); + spTask->GetMiniSnapshot(&dd); - if ((dd.m_uiStatus & ST_STEP_MASK) != ST_FINISHED && (dd.m_uiStatus & ST_STEP_MASK) != ST_CANCELLED) + if((dd.m_uiStatus & ST_STEP_MASK) != ST_FINISHED && (dd.m_uiStatus & ST_STEP_MASK) != ST_CANCELLED) { - pItem=m_ctlStatus.GetItemAddress(index++); + pItem = m_ctlStatus.GetItemAddress(index++); // load if ((dd.m_uiStatus & ST_WORKING_MASK) == ST_ERROR) @@ -202,7 +202,7 @@ pItem->m_strText=dd.m_fi.GetFileName(); pItem->m_uiPos=dd.m_nPercent; - pItem->m_pTask=pTask; + pItem->m_spTask = spTask; } } } @@ -245,7 +245,7 @@ pItem->m_crColor=GetSysColor(COLOR_HIGHLIGHT); pItem->m_strText=GetResManager().LoadString(IDS_MINIVIEWALL_STRING); pItem->m_uiPos=m_pTasks->GetPercent(); - pItem->m_pTask=NULL; + pItem->m_spTask.reset(); // get rid of the rest m_ctlStatus.SetSmoothProgress(GetConfig().get_bool(PP_MVUSESMOOTHPROGRESS)); @@ -406,9 +406,9 @@ if (iSel == LB_ERR || (size_t)iSel >= pDlg->m_ctlStatus.m_vItems.size()) return; - CTask* pTask; - if ( (pTask=pDlg->m_ctlStatus.m_vItems.at(iSel)->m_pTask) != NULL) - pTask->PauseProcessing(); + CTaskPtr spTask = pDlg->m_ctlStatus.m_vItems.at(iSel)->m_spTask; + if(spTask) + spTask->PauseProcessing(); else pDlg->m_pTasks->TasksPauseProcessing(); @@ -513,13 +513,13 @@ int iSel=pDlg->m_ctlStatus.GetCurSel(); if (iSel == LB_ERR || (size_t)iSel >= pDlg->m_ctlStatus.m_vItems.size()) return; - CTask* pTask; - if ( (pTask=pDlg->m_ctlStatus.m_vItems.at(iSel)->m_pTask) != NULL) + CTaskPtr spTask = pDlg->m_ctlStatus.m_vItems.at(iSel)->m_spTask; + if (spTask) { - if (pTask->GetStatus(ST_WAITING_MASK) & ST_WAITING) - pTask->SetForceFlag(true); + if(spTask->GetStatus(ST_WAITING_MASK) & ST_WAITING) + spTask->SetForceFlag(true); else - pTask->ResumeProcessing(); + spTask->ResumeProcessing(); } else pDlg->m_pTasks->TasksResumeProcessing(); @@ -557,9 +557,9 @@ int iSel=pDlg->m_ctlStatus.GetCurSel(); if (iSel == LB_ERR || (size_t)iSel >= pDlg->m_ctlStatus.m_vItems.size()) return; - CTask* pTask; - if ( (pTask=pDlg->m_ctlStatus.m_vItems.at(iSel)->m_pTask) != NULL) - pTask->CancelProcessing(); + CTaskPtr spTask = pDlg->m_ctlStatus.m_vItems.at(iSel)->m_spTask; + if(spTask) + spTask->CancelProcessing(); else pDlg->m_pTasks->TasksCancelProcessing(); break; @@ -611,9 +611,9 @@ int iSel=pDlg->m_ctlStatus.GetCurSel(); if (iSel == LB_ERR || (size_t)iSel >= pDlg->m_ctlStatus.m_vItems.size()) return; - CTask* pTask; - if ( (pTask=pDlg->m_ctlStatus.m_vItems.at(iSel)->m_pTask) != NULL) - pTask->RestartProcessing(); + CTaskPtr spTask = pDlg->m_ctlStatus.m_vItems.at(iSel)->m_spTask; + if(spTask) + spTask->RestartProcessing(); else pDlg->m_pTasks->TasksRestartProcessing(); break; @@ -801,13 +801,13 @@ void CMiniViewDlg::OnDblclkProgressList() { - int iSel=m_ctlStatus.GetCurSel(); - if (iSel == LB_ERR || (size_t)iSel >= m_ctlStatus.m_vItems.size()) + int iSel = m_ctlStatus.GetCurSel(); + if(iSel == LB_ERR || (size_t)iSel >= m_ctlStatus.m_vItems.size()) return; - CTask* pTask; - pTask=m_ctlStatus.m_vItems.at(iSel)->m_pTask; - GetParent()->PostMessage(WM_MINIVIEWDBLCLK, 0, (LPARAM)pTask); + CTaskPtr spTask = m_ctlStatus.m_vItems.at(iSel)->m_spTask; + + GetParent()->PostMessage(WM_MINIVIEWDBLCLK, 0, (LPARAM)spTask->GetSessionUniqueID()); } void CMiniViewDlg::OnLanguageChanged() Index: src/ch/ProgressListBox.cpp =================================================================== diff -u -r9352ed0c4fe447a36bc728640c307be6d41455fd -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/ProgressListBox.cpp (.../ProgressListBox.cpp) (revision 9352ed0c4fe447a36bc728640c307be6d41455fd) +++ src/ch/ProgressListBox.cpp (.../ProgressListBox.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -17,6 +17,7 @@ * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "stdafx.h" +#include "task.h" #include "ProgressListBox.h" #include "MemDC.h" Index: src/ch/ProgressListBox.h =================================================================== diff -u -r449a5b399ab21ca0d06050b47b264f2f704af966 -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/ProgressListBox.h (.../ProgressListBox.h) (revision 449a5b399ab21ca0d06050b47b264f2f704af966) +++ src/ch/ProgressListBox.h (.../ProgressListBox.h) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -19,8 +19,6 @@ #ifndef __PROGRESSLISTBOX_H__ #define __PROGRESSLISTBOX_H__ -class CTask; - ///////////////////////////////////////////////////////////////////////////// // CProgressListBox window struct _PROGRESSITEM_ @@ -32,7 +30,7 @@ COLORREF m_crColor; - CTask* m_pTask; + CTaskPtr m_spTask; }; class CProgressListBox : public CListBox Index: src/ch/ReplacePathsDlg.cpp =================================================================== diff -u -r9352ed0c4fe447a36bc728640c307be6d41455fd -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/ReplacePathsDlg.cpp (.../ReplacePathsDlg.cpp) (revision 9352ed0c4fe447a36bc728640c307be6d41455fd) +++ src/ch/ReplacePathsDlg.cpp (.../ReplacePathsDlg.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -18,10 +18,10 @@ ***************************************************************************/ #include "stdafx.h" #include "resource.h" +#include "task.h" #include "ReplacePathsDlg.h" #include "dialogs.h" #include "ch.h" -#include "task.h" #ifdef _DEBUG #define new DEBUG_NEW @@ -82,9 +82,9 @@ InitializeResizableControls(); - for(size_t stIndex = 0; stIndex < m_pTask->GetClipboardDataSize(); ++stIndex) + for(size_t stIndex = 0; stIndex < m_spTask->GetClipboardDataSize(); ++stIndex) { - m_ctlPathsList.AddString(m_pTask->GetClipboardData(stIndex)->GetPath()); + m_ctlPathsList.AddString(m_spTask->GetClipboardData(stIndex)->GetPath()); } return TRUE; Index: src/ch/ReplacePathsDlg.h =================================================================== diff -u -r9c71c0a84781c524c0091ee86914d5cc3bbf5190 -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/ReplacePathsDlg.h (.../ReplacePathsDlg.h) (revision 9c71c0a84781c524c0091ee86914d5cc3bbf5190) +++ src/ch/ReplacePathsDlg.h (.../ReplacePathsDlg.h) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -30,7 +30,7 @@ public: CReplacePathsDlg(); // standard constructor - CTask* m_pTask; + CTaskPtr m_spTask; // Dialog Data //{{AFX_DATA(CReplacePathsDlg) enum { IDD = IDD_REPLACE_PATHS_DIALOG }; Index: src/ch/StatusDlg.cpp =================================================================== diff -u -r9352ed0c4fe447a36bc728640c307be6d41455fd -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/StatusDlg.cpp (.../StatusDlg.cpp) (revision 9352ed0c4fe447a36bc728640c307be6d41455fd) +++ src/ch/StatusDlg.cpp (.../StatusDlg.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -164,7 +164,7 @@ size_t stIndex = 0; while(stIndex < m_pTasks->GetSize()) { - if(m_pTasks->GetAt(stIndex) == m_pInitialSelection) + if(m_pTasks->GetAt(stIndex) == m_spInitialSelection) { m_ctlStatusList.SetItemState(boost::numeric_cast(stIndex), LVIS_SELECTED, LVIS_SELECTED); break; @@ -224,21 +224,25 @@ CLanguageDialog::OnTimer(nIDEvent); } -void CStatusDlg::AddTaskInfo(int nPos, CTask *pTask, DWORD dwCurrentTime) +void CStatusDlg::AddTaskInfo(int nPos, const CTaskPtr& spTask, DWORD dwCurrentTime) { + _ASSERTE(spTask != NULL); + if(spTask == NULL) + return; + // index to string _itot(nPos, m_szData, 10); // get data snapshot from task - pTask->GetSnapshot(&td); + spTask->GetSnapshot(&td); // index subitem lvi.mask=LVIF_TEXT | LVIF_PARAM | LVIF_IMAGE; lvi.iItem=nPos; lvi.iSubItem=0; lvi.pszText=td.m_szStatusText; lvi.cchTextMax=lstrlen(lvi.pszText); - lvi.lParam=reinterpret_cast(pTask); + lvi.lParam = spTask->GetSessionUniqueID(); lvi.iImage=GetImageFromStatus(td.m_uiStatus); if (nPos < m_ctlStatusList.GetItemCount()) m_ctlStatusList.SetItem(&lvi); @@ -271,7 +275,7 @@ m_ctlStatusList.SetItem(&lvi); // right side update - if (pTask == pSelectedItem && GetConfig().get_bool(PP_STATUSSHOWDETAILS)) + if(spTask == m_spSelectedItem && GetConfig().get_bool(PP_STATUSSHOWDETAILS)) { // data that can be changed by a thread GetDlgItem(IDC_OPERATION_STATIC)->SetWindowText(td.m_szStatusText); // operation @@ -335,56 +339,42 @@ // data that can be changed only by user from outside the thread // refresh only when there are new selected item -// if (pTask != m_pLastSelected) +// if (spTask != m_spLastSelected) { GetDlgItem(IDC_DESTINATION_STATIC)->SetWindowText(td.m_pdpDestPath->GetPath()); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(td.m_nPriority))); GetDlgItem(IDC_ASSOCIATEDFILES__STATIC)->SetWindowText(*td.m_pstrUniqueName+_T(".atd (.atp, .log)")); } - // refresh m_pLastSelected - m_pLastSelected=pTask; + // refresh m_spLastSelected + m_spLastSelected = spTask; } } void CStatusDlg::OnSetBuffersizeButton() { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL ) + CTaskPtr spTask = GetSelectedItemPointer(); + if(!spTask) return; CBufferSizeDlg dlg; - dlg.m_bsSizes=*pTask->GetBufferSizes(); - dlg.m_iActiveIndex=pTask->GetCurrentBufferIndex(); - if (dlg.DoModal() == IDOK) - { - // if the task has been deleted - skip - if ( pTask != GetSelectedItemPointer() ) - { - TRACE("Task were finished and deleted when trying to change buffer sizes"); - return; - } - - TRACE("bOnlyDefault=%d\n", dlg.m_bsSizes.m_bOnlyDefault); - pTask->SetBufferSizes(&dlg.m_bsSizes); - } + dlg.m_bsSizes = *spTask->GetBufferSizes(); + dlg.m_iActiveIndex = spTask->GetCurrentBufferIndex(); + if(dlg.DoModal() == IDOK) + spTask->SetBufferSizes(&dlg.m_bsSizes); } -CTask* CStatusDlg::GetSelectedItemPointer() +CTaskPtr CStatusDlg::GetSelectedItemPointer() { -// TRACE("inside GetSelectedItemPointer()\n"); // returns ptr to a CTask for a given element in listview - if (m_ctlStatusList.GetSelectedCount() == 1) + if(m_ctlStatusList.GetSelectedCount() == 1) { - POSITION pos=m_ctlStatusList.GetFirstSelectedItemPosition(); - int nPos=m_ctlStatusList.GetNextSelectedItem(pos); - CTask* pSelectedItem=reinterpret_cast(m_ctlStatusList.GetItemData(nPos)); -// if (AfxIsValidAddress(pSelectedItem, sizeof(CTask))) - return pSelectedItem; + POSITION pos = m_ctlStatusList.GetFirstSelectedItemPosition(); + int nPos = m_ctlStatusList.GetNextSelectedItem(pos); + return m_pTasks->GetTaskBySessionUniqueID(m_ctlStatusList.GetItemData(nPos)); } -// TRACE("exiting GetSelectedItemPointer()\n"); - return NULL; + return CTaskPtr(); } void CStatusDlg::OnRollUnrollButton() @@ -437,18 +427,18 @@ void CStatusDlg::ApplyButtonsState() { // remember ptr to CTask - pSelectedItem=GetSelectedItemPointer(); + m_spSelectedItem=GetSelectedItemPointer(); bool bShowLog=GetConfig().get_bool(PP_CMCREATELOG); // set status of buttons pause/resume/cancel - if (pSelectedItem != NULL) + if (m_spSelectedItem != NULL) { GetDlgItem(IDC_RESTART_BUTTON)->EnableWindow(true); GetDlgItem(IDC_SHOW_LOG_BUTTON)->EnableWindow(bShowLog); GetDlgItem(IDC_DELETE_BUTTON)->EnableWindow(true); - if (pSelectedItem->GetStatus(ST_STEP_MASK) == ST_FINISHED - || pSelectedItem->GetStatus(ST_STEP_MASK) == ST_CANCELLED) + if (m_spSelectedItem->GetStatus(ST_STEP_MASK) == ST_FINISHED + || m_spSelectedItem->GetStatus(ST_STEP_MASK) == ST_CANCELLED) { GetDlgItem(IDC_CANCEL_BUTTON)->EnableWindow(false); GetDlgItem(IDC_PAUSE_BUTTON)->EnableWindow(false); @@ -457,15 +447,15 @@ else { // pause/resume - if (pSelectedItem->GetStatus(ST_WORKING_MASK) & ST_PAUSED) + if (m_spSelectedItem->GetStatus(ST_WORKING_MASK) & ST_PAUSED) { GetDlgItem(IDC_PAUSE_BUTTON)->EnableWindow(false); GetDlgItem(IDC_RESUME_BUTTON)->EnableWindow(true); } else { GetDlgItem(IDC_PAUSE_BUTTON)->EnableWindow(true); - if (pSelectedItem->GetStatus(ST_WAITING_MASK) & ST_WAITING) + if (m_spSelectedItem->GetStatus(ST_WAITING_MASK) & ST_WAITING) GetDlgItem(IDC_RESUME_BUTTON)->EnableWindow(true); else GetDlgItem(IDC_RESUME_BUTTON)->EnableWindow(false); @@ -514,37 +504,37 @@ if (LOWORD(wParam) >= ID_POPUP_TIME_CRITICAL && LOWORD(wParam) <= ID_POPUP_IDLE) { // processing priority - if ( (pSelectedItem=GetSelectedItemPointer()) == NULL ) + if ( (m_spSelectedItem=GetSelectedItemPointer()) == NULL ) return ictranslate::CLanguageDialog::OnCommand(wParam, lParam); switch (LOWORD(wParam)) { case ID_POPUP_TIME_CRITICAL: - pSelectedItem->SetPriority(THREAD_PRIORITY_TIME_CRITICAL); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_TIME_CRITICAL); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_TIME_CRITICAL))); break; case ID_POPUP_HIGHEST: - pSelectedItem->SetPriority(THREAD_PRIORITY_HIGHEST); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_HIGHEST); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_HIGHEST))); break; case ID_POPUP_ABOVE_NORMAL: - pSelectedItem->SetPriority(THREAD_PRIORITY_ABOVE_NORMAL); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_ABOVE_NORMAL); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_ABOVE_NORMAL))); break; case ID_POPUP_NORMAL: - pSelectedItem->SetPriority(THREAD_PRIORITY_NORMAL); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_NORMAL); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_NORMAL))); break; case ID_POPUP_BELOW_NORMAL: - pSelectedItem->SetPriority(THREAD_PRIORITY_BELOW_NORMAL); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_BELOW_NORMAL); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_BELOW_NORMAL))); break; case ID_POPUP_LOWEST: - pSelectedItem->SetPriority(THREAD_PRIORITY_LOWEST); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_LOWEST); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_LOWEST))); break; case ID_POPUP_IDLE: - pSelectedItem->SetPriority(THREAD_PRIORITY_IDLE); + m_spSelectedItem->SetPriority(THREAD_PRIORITY_IDLE); GetDlgItem(IDC_PRIORITY_STATIC)->SetWindowText(GetResManager().LoadString(IDS_PRIORITY0_STRING+PriorityToIndex(THREAD_PRIORITY_IDLE))); break; } @@ -555,83 +545,71 @@ void CStatusDlg::OnPauseButton() { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL ) - return; + CTaskPtr spTask = GetSelectedItemPointer(); + if(spTask) + { + TRACE("PauseProcessing call...\n"); + spTask->PauseProcessing(); - TRACE("PauseProcessing call...\n"); - pTask->PauseProcessing(); - - RefreshStatus(); + RefreshStatus(); + } } void CStatusDlg::OnResumeButton() { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL ) - return; + CTaskPtr spTask = GetSelectedItemPointer(); + if(spTask) + { + if(spTask->GetStatus(ST_WAITING_MASK) & ST_WAITING) + spTask->SetForceFlag(); + else + spTask->ResumeProcessing(); - TRACE("ResumeProcessing call "); - if (pTask->GetStatus(ST_WAITING_MASK) & ST_WAITING) - { - TRACE("by setting force flag\n"); - pTask->SetForceFlag(); - } - else - { - TRACE("by function ResumeProcessing\n"); - pTask->ResumeProcessing(); - } - - RefreshStatus(); + RefreshStatus(); + } } void CStatusDlg::OnCancelButton() { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) != NULL ) - { - TRACE("CancelProcessing call...\n"); - pTask->CancelProcessing(); - } - RefreshStatus(); + CTaskPtr spTask = GetSelectedItemPointer(); + if(spTask) + { + spTask->CancelProcessing(); + RefreshStatus(); + } } void CStatusDlg::OnRestartButton() { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL ) - return; - - TRACE("RestartProcessing call...\n"); - pTask->RestartProcessing(); - RefreshStatus(); + CTaskPtr spTask = GetSelectedItemPointer(); + if(spTask) + { + spTask->RestartProcessing(); + RefreshStatus(); + } } void CStatusDlg::OnDeleteButton() { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL ) - return; + CTaskPtr spTask = GetSelectedItemPointer(); + if(spTask) + { + UINT uiStatus = spTask->GetStatus(ST_STEP_MASK); + if((uiStatus & ST_STEP_MASK) != ST_FINISHED && (uiStatus & ST_STEP_MASK) != ST_CANCELLED) + { + // ask if cancel + if(MsgBox(IDS_CONFIRMCANCEL_STRING, MB_OKCANCEL | MB_ICONQUESTION) == IDOK) + { + // cancel + spTask->CancelProcessing(); + } + else + return; + } - UINT uiStatus=pTask->GetStatus(ST_STEP_MASK); - if ( (uiStatus & ST_STEP_MASK) != ST_FINISHED && (uiStatus & ST_STEP_MASK) != ST_CANCELLED ) - { - // ask if cancel - if (MsgBox(IDS_CONFIRMCANCEL_STRING, MB_OKCANCEL | MB_ICONQUESTION) == IDOK) - { - // cancel - if ( (pTask=GetSelectedItemPointer()) == NULL ) - return; - - pTask->CancelProcessing(); - } - else - return; - } - - m_pTasks->RemoveFinished(&pTask); - RefreshStatus(); + m_pTasks->RemoveFinished(spTask); + RefreshStatus(); + } } void CStatusDlg::OnPauseAllButton() @@ -678,11 +656,11 @@ break; case VK_SPACE: { - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL ) + CTaskPtr spTask = GetSelectedItemPointer(); + if (!spTask) return; - if (pTask->GetStatus(ST_WORKING_MASK) & ST_PAUSED) + if(spTask->GetStatus(ST_WORKING_MASK) & ST_PAUSED) OnResumeButton(); else OnPauseButton(); @@ -731,7 +709,7 @@ void CStatusDlg::RefreshStatus() { // remember address of a current selection - pSelectedItem=GetSelectedItemPointer(); + m_spSelectedItem=GetSelectedItemPointer(); // current time DWORD dwCurrentTime=GetTickCount(); @@ -787,7 +765,7 @@ if (m_ctlStatusList.GetSelectedCount() == 0) { EnableControls(false); - m_pLastSelected=NULL; + m_spLastSelected.reset(); m_i64LastProcessed=0; } else @@ -834,24 +812,24 @@ void CStatusDlg::OnPopupReplacePaths() { // check if there's a selection currently - if ( (pSelectedItem=GetSelectedItemPointer()) != NULL ) + if ( (m_spSelectedItem=GetSelectedItemPointer()) != NULL ) { - if (pSelectedItem->GetStatus(ST_WORKING_MASK) & ST_PAUSED) + if (m_spSelectedItem->GetStatus(ST_WORKING_MASK) & ST_PAUSED) { bool bContinue=false; - if (pSelectedItem->GetStatus(ST_WORKING_MASK) == ST_ERROR) + if (m_spSelectedItem->GetStatus(ST_WORKING_MASK) == ST_ERROR) { - pSelectedItem->PauseProcessing(); + m_spSelectedItem->PauseProcessing(); bContinue=true; } // assuming here that there's selection and task is paused CReplacePathsDlg dlg; - dlg.m_pTask=pSelectedItem; + dlg.m_spTask=m_spSelectedItem; if (dlg.DoModal() == IDOK) { // change 'no case' - int iClipboard=pSelectedItem->ReplaceClipboardStrings(dlg.m_strSource, dlg.m_strDest); + int iClipboard=m_spSelectedItem->ReplaceClipboardStrings(dlg.m_strSource, dlg.m_strDest); ictranslate::CFormat fmt(GetResManager().LoadString(IDS_REPLACEPATHSTEXT_STRING)); fmt.SetParam(_t("%count"), iClipboard); @@ -860,7 +838,7 @@ // resume if earlier was an error if (bContinue) - pSelectedItem->ResumeProcessing(); + m_spSelectedItem->ResumeProcessing(); } else MsgBox(IDS_TASKNOTPAUSED_STRING); @@ -872,16 +850,15 @@ void CStatusDlg::OnShowLogButton() { // show log - CTask* pTask; - if ( (pTask=GetSelectedItemPointer()) == NULL || !GetConfig().get_bool(PP_CMCREATELOG)) + CTaskPtr spTask = GetSelectedItemPointer(); + if (!spTask || !GetConfig().get_bool(PP_CMCREATELOG)) return; - // call what's needed - unsigned long lResult=(unsigned long)(ShellExecute(this->m_hWnd, _T("open"), _T("notepad.exe"), - CString(pTask->GetTaskPath())+pTask->GetUniqueName()+_T(".log"), NULL, SW_SHOWNORMAL)); - if (lResult < 32) + unsigned long lResult = (unsigned long)(ShellExecute(this->m_hWnd, _T("open"), _T("notepad.exe"), + CString(spTask->GetTaskPath()) + spTask->GetUniqueName() + _T(".log"), NULL, SW_SHOWNORMAL)); + if(lResult < 32) { - CString str=CString(pTask->GetTaskPath())+pTask->GetUniqueName()+_T(".log"); + CString str = CString(spTask->GetTaskPath()) + spTask->GetUniqueName()+_T(".log"); ictranslate::CFormat fmt(GetResManager().LoadString(IDS_SHELLEXECUTEERROR_STRING)); fmt.SetParam(_t("%errno"), lResult); fmt.SetParam(_t("%path"), str); Index: src/ch/StatusDlg.h =================================================================== diff -u -r11621f18af6a7b1d486a7d6a576b97d4d09e8e96 -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/StatusDlg.h (.../StatusDlg.h) (revision 11621f18af6a7b1d486a7d6a576b97d4d09e8e96) +++ src/ch/StatusDlg.h (.../StatusDlg.h) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -41,15 +41,15 @@ void ApplyButtonsState(); void ApplyDisplayDetails(bool bInitial=false); - CTask* GetSelectedItemPointer(); + CTaskPtr GetSelectedItemPointer(); - void AddTaskInfo(int nPos, CTask *pTask, DWORD dwCurrentTime); + void AddTaskInfo(int nPos, const CTaskPtr& spTask, DWORD dwCurrentTime); void EnableControls(bool bEnable=true); CTaskArray* m_pTasks; - CTask* pSelectedItem; - const CTask *m_pLastSelected; - const CTask* m_pInitialSelection; + CTaskPtr m_spSelectedItem; + CTaskPtr m_spLastSelected; + CTaskPtr m_spInitialSelection; TCHAR m_szData[_MAX_PATH]; TCHAR m_szTimeBuffer1[40]; Index: src/ch/task.cpp =================================================================== diff -u -r678a716a4ed83d5790a407ce60dfcf7d8ca703fa -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/task.cpp (.../task.cpp) (revision 678a716a4ed83d5790a407ce60dfcf7d8ca703fa) +++ src/ch/task.cpp (.../task.cpp) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -25,6 +25,7 @@ #include #include #include +#include #include // assume max sectors of 4kB (for rounding) @@ -64,7 +65,7 @@ //////////////////////////////////////////////////////////////////////////// // CTask members -CTask::CTask(chcore::IFeedbackHandler* piFeedbackHandler, const TASK_CREATE_DATA *pCreateData) : +CTask::CTask(chcore::IFeedbackHandler* piFeedbackHandler, const TASK_CREATE_DATA *pCreateData, size_t stSessionUniqueID) : m_log(), m_piFeedbackHandler(piFeedbackHandler), m_files(m_clipboard), @@ -91,7 +92,8 @@ m_bForce(false), m_bContinue(false), m_bSaved(false), - m_lOsError(0) + m_lOsError(0), + m_stSessionUniqueID(stSessionUniqueID) { BOOST_ASSERT(piFeedbackHandler); @@ -1126,12 +1128,12 @@ //////////////////////////////////////////////////////////////////////////////// // CTaskArray members CTaskArray::CTaskArray() : -CArray(), -m_uhRange(0), -m_uhPosition(0), -m_uiOperationsPending(0), -m_lFinished(0), -m_piFeedbackFactory(NULL) + m_uhRange(0), + m_uhPosition(0), + m_uiOperationsPending(0), + m_lFinished(0), + m_piFeedbackFactory(NULL), + m_stNextSessionUniqueID(0) { } @@ -1152,76 +1154,75 @@ m_piFeedbackFactory = piFeedbackHandlerFactory; } -CTask* CTaskArray::CreateTask() +CTaskPtr CTaskArray::CreateTask() { BOOST_ASSERT(m_piFeedbackFactory); if(!m_piFeedbackFactory) - return NULL; + return CTaskPtr(); chcore::IFeedbackHandler* piHandler = m_piFeedbackFactory->Create(); if(!piHandler) - return NULL; + return CTaskPtr(); - CTask* pTask = NULL; - try - { - pTask = new CTask(piHandler, &m_tcd); - } - catch(...) - { - // piHandler->Delete(); - throw; - } - - return pTask; + CTaskPtr spTask = boost::make_shared(piHandler, &m_tcd, m_stNextSessionUniqueID++); + return spTask; } size_t CTaskArray::GetSize() { m_cs.Lock(); - size_t stSize = m_nSize; + size_t stSize = m_vTasks.size(); m_cs.Unlock(); return stSize; } -size_t CTaskArray::GetUpperBound( ) +CTaskPtr CTaskArray::GetAt(size_t nIndex) { + _ASSERTE(nIndex >= 0 && nIndex < (size_t)m_vTasks.size()); + if(nIndex >= m_vTasks.size()) + THROW(_t("Invalid argument"), 0, 0, 0); + m_cs.Lock(); - size_t stUpper = m_nSize; + CTaskPtr spTask = m_vTasks.at(nIndex); m_cs.Unlock(); - return stUpper - 1; + return spTask; } -void CTaskArray::SetSize(size_t nNewSize, int nGrowBy) +CTaskPtr CTaskArray::GetTaskBySessionUniqueID(size_t stSessionUniqueID) { - m_cs.Lock(); - (static_cast*>(this))->SetSize(nNewSize, nGrowBy); - m_cs.Unlock(); -} + CTaskPtr spFoundTask; -CTask* CTaskArray::GetAt(size_t nIndex) -{ - ASSERT(nIndex >= 0 && nIndex < (size_t)m_nSize); - m_cs.Lock(); - CTask* pTask = m_pData[nIndex]; - m_cs.Unlock(); + m_cs.Lock(); + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + if(spTask->GetSessionUniqueID() == stSessionUniqueID) + { + spFoundTask = spTask; + break; + } + } + m_cs.Unlock(); - return pTask; + return spFoundTask; } -size_t CTaskArray::Add(CTask* newElement) +size_t CTaskArray::Add(const CTaskPtr& spNewTask) { - if(!newElement) + if(!spNewTask) THROW(_t("Invalid argument"), 0, 0, 0); + m_cs.Lock(); // here we know load succeeded - newElement->SetTaskPath(m_strTasksDir.c_str()); + spNewTask->SetTaskPath(m_strTasksDir.c_str()); - m_uhRange+=newElement->GetAllSize(); - m_uhPosition+=newElement->GetProcessedSize(); - size_t pos = (static_cast*>(this))->Add(newElement); + m_vTasks.push_back(spNewTask); + + m_uhRange += spNewTask->GetAllSize(); + m_uhPosition += spNewTask->GetProcessedSize(); + + size_t pos = m_vTasks.size() - 1; m_cs.Unlock(); return pos; @@ -1230,135 +1231,143 @@ void CTaskArray::RemoveAt(size_t stIndex, size_t stCount) { m_cs.Lock(); - for(size_t i = stIndex; i < stIndex + stCount; i++) - { - CTask* pTask = GetAt(i); + try + { + _ASSERTE(stIndex >= m_vTasks.size() || stIndex + stCount > m_vTasks.size()); + if(stIndex >= m_vTasks.size() || stIndex + stCount > m_vTasks.size()) + THROW(_t("Invalid argument"), 0, 0, 0); - // kill task if needed - pTask->KillThread(); + for(std::vector::iterator iterTask = m_vTasks.begin() + stIndex; iterTask != m_vTasks.begin() + stIndex + stCount; ++iterTask) + { + CTaskPtr& spTask = *iterTask; - m_uhRange -= pTask->GetAllSize(); - m_uhPosition -= pTask->GetProcessedSize(); + // kill task if needed + spTask->KillThread(); - delete pTask; - } + m_uhRange -= spTask->GetAllSize(); + m_uhPosition -= spTask->GetProcessedSize(); + } - // remove elements from array - (static_cast*>(this))->RemoveAt(stIndex, stCount); + // remove elements from array + m_vTasks.erase(m_vTasks.begin() + stIndex, m_vTasks.begin() + stIndex + stCount); + } + catch(...) + { + m_cs.Unlock(); + throw; + } m_cs.Unlock(); } void CTaskArray::RemoveAll() { - m_cs.Lock(); - CTask* pTask; + m_cs.Lock(); - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) - { - GetAt(stIndex)->SetKillFlag(); // send an info about finishing - } + StopAllTasks(); - // wait for finishing and get rid of it - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) - { - pTask=GetAt(stIndex); + m_vTasks.clear(); - // wait - while(!pTask->GetKilledFlag()) - Sleep(10); - - pTask->CleanupAfterKill(); - - m_uhRange-=pTask->GetAllSize(); - m_uhPosition-=pTask->GetProcessedSize(); - - // delete data - delete pTask; - } - - (static_cast*>(this))->RemoveAll(); - m_cs.Unlock(); + m_cs.Unlock(); } void CTaskArray::RemoveAllFinished() { m_cs.Lock(); - size_t i = GetSize(); - while(i--) + size_t stIndex = m_vTasks.size(); + while(stIndex--) { - CTask* pTask = GetAt(i); + CTaskPtr spTask = m_vTasks.at(stIndex); // delete only when the thread is finished - if ( (pTask->GetStatus(ST_STEP_MASK) == ST_FINISHED || pTask->GetStatus(ST_STEP_MASK) == ST_CANCELLED) - && pTask->GetKilledFlag()) + if((spTask->GetStatus(ST_STEP_MASK) == ST_FINISHED || spTask->GetStatus(ST_STEP_MASK) == ST_CANCELLED) + && spTask->GetKilledFlag()) { - m_uhRange-=pTask->GetAllSize(); - m_uhPosition-=pTask->GetProcessedSize(); + m_uhRange -= spTask->GetAllSize(); + m_uhPosition -= spTask->GetProcessedSize(); // delete associated files - pTask->DeleteProgress(m_strTasksDir.c_str()); + spTask->DeleteProgress(m_strTasksDir.c_str()); - delete pTask; - - static_cast*>(this)->RemoveAt(i); + m_vTasks.erase(m_vTasks.begin() + stIndex); } } m_cs.Unlock(); } -void CTaskArray::RemoveFinished(CTask** pSelTask) +void CTaskArray::RemoveFinished(const CTaskPtr& spSelTask) { m_cs.Lock(); - for(size_t stIndex=0; stIndex < GetSize(); ++stIndex) + for(std::vector::iterator iterTask = m_vTasks.begin(); iterTask != m_vTasks.end(); ++iterTask) { - CTask* pTask = GetAt(stIndex); + CTaskPtr& spTask = *iterTask; - if (pTask == *pSelTask && (pTask->GetStatus(ST_STEP_MASK) == ST_FINISHED || pTask->GetStatus(ST_STEP_MASK) == ST_CANCELLED)) + if(spTask == spSelTask && (spTask->GetStatus(ST_STEP_MASK) == ST_FINISHED || spTask->GetStatus(ST_STEP_MASK) == ST_CANCELLED)) { // kill task if needed - pTask->KillThread(); + spTask->KillThread(); - m_uhRange-=pTask->GetAllSize(); - m_uhPosition-=pTask->GetProcessedSize(); + m_uhRange -= spTask->GetAllSize(); + m_uhPosition -= spTask->GetProcessedSize(); // delete associated files - pTask->DeleteProgress(m_strTasksDir.c_str()); + spTask->DeleteProgress(m_strTasksDir.c_str()); - // delete data - delete pTask; + m_vTasks.erase(iterTask); - static_cast*>(this)->RemoveAt(stIndex); - m_cs.Unlock(); return; } } m_cs.Unlock(); } +void CTaskArray::StopAllTasks() +{ + m_cs.Lock(); + + // kill all unfinished tasks - send kill request + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + spTask->SetKillFlag(); + } + + // wait for finishing + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + while(!spTask->GetKilledFlag()) + Sleep(10); + spTask->CleanupAfterKill(); + } + m_cs.Unlock(); +} + void CTaskArray::SaveData() { m_cs.Lock(); - for (int i=0;iStore(true); + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + spTask->Store(true); + } m_cs.Unlock(); } void CTaskArray::SaveProgress() { m_cs.Lock(); - for (int i=0;iStore(false); + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + spTask->Store(false); + } m_cs.Unlock(); } void CTaskArray::LoadDataProgress() { m_cs.Lock(); CFileFind finder; - CTask* pTask; + CTaskPtr spTask; CString strPath; BOOL bWorking=finder.FindFile(CString(m_strTasksDir.c_str())+_T("*.atd")); @@ -1367,28 +1376,26 @@ bWorking = finder.FindNextFile(); // load data - pTask = CreateTask(); - + spTask = CreateTask(); try { strPath = finder.GetFilePath(); - pTask->Load(strPath, true); + spTask->Load(strPath, true); strPath = strPath.Left(strPath.GetLength() - 4); strPath += _T(".atp"); - pTask->Load(strPath, false); + spTask->Load(strPath, false); // add read task to array - Add(pTask); + Add(spTask); } catch(std::exception& e) { CString strFmt; strFmt.Format(_T("Cannot load task data: %s (reason: %S)"), strPath, e.what()); LOG_ERROR(strFmt); - delete pTask; } } finder.Close(); @@ -1398,16 +1405,18 @@ void CTaskArray::TasksBeginProcessing() { - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) { - GetAt(stIndex)->BeginProcessing(); + spTask->BeginProcessing(); } } void CTaskArray::TasksPauseProcessing() { - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) - GetAt(stIndex)->PauseProcessing(); + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + spTask->PauseProcessing(); + } } void CTaskArray::TasksResumeProcessing() @@ -1418,32 +1427,36 @@ void CTaskArray::TasksRestartProcessing() { - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) - GetAt(stIndex)->RestartProcessing(); + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + spTask->RestartProcessing(); + } } bool CTaskArray::TasksRetryProcessing(bool bOnlyErrors/*=false*/, UINT uiInterval) { bool bChanged=false; - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) { - if (GetAt(stIndex)->RetryProcessing(bOnlyErrors, uiInterval)) - bChanged=true; + if(spTask->RetryProcessing(bOnlyErrors, uiInterval)) + bChanged = true; } return bChanged; } void CTaskArray::TasksCancelProcessing() { - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) - GetAt(stIndex)->CancelProcessing(); + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) + { + spTask->CancelProcessing(); + } } ull_t CTaskArray::GetPosition() { m_cs.Lock(); - ull_t rv=m_uhPosition; + ull_t rv = m_uhPosition; m_cs.Unlock(); return rv; @@ -1492,9 +1505,9 @@ bFlag=false; else { - for(size_t stIndex = 0; stIndex < GetSize(); ++stIndex) + BOOST_FOREACH(CTaskPtr& spTask, m_vTasks) { - uiStatus=GetAt(stIndex)->GetStatus(); + uiStatus = spTask->GetStatus(); bFlag=((uiStatus & ST_STEP_MASK) == ST_FINISHED || (uiStatus & ST_STEP_MASK) == ST_CANCELLED || (uiStatus & ST_WORKING_MASK) == ST_PAUSED || ((uiStatus & ST_WORKING_MASK) == ST_ERROR && !GetConfig().get_bool(PP_CMAUTORETRYONERROR))); Index: src/ch/task.h =================================================================== diff -u -r678a716a4ed83d5790a407ce60dfcf7d8ca703fa -rf703b71b8c856e2538283555e9fdbc84918677c3 --- src/ch/task.h (.../task.h) (revision 678a716a4ed83d5790a407ce60dfcf7d8ca703fa) +++ src/ch/task.h (.../task.h) (revision f703b71b8c856e2538283555e9fdbc84918677c3) @@ -232,7 +232,7 @@ class CTask { public: - CTask(chcore::IFeedbackHandler* piFeedbackHandler, const TASK_CREATE_DATA *pCreateData); + CTask(chcore::IFeedbackHandler* piFeedbackHandler, const TASK_CREATE_DATA *pCreateData, size_t stSessionUniqueID); ~CTask(); int OnBeginTask(); @@ -363,6 +363,8 @@ void SetContinueFlag(bool bFlag=true); bool GetContinueFlag(); + size_t GetSessionUniqueID() const { return m_stSessionUniqueID; } + protected: static UINT ThrdProc(LPVOID pParam); static void CheckForWaitState(CTask* pTask); @@ -435,9 +437,13 @@ tstring_t m_strTaskBasePath; // base path at which the files will be stored bool m_bSaved; // has the state been saved ('til next modification) + size_t m_stSessionUniqueID; + CCriticalSection* m_pcs; // protects *m_pnTasksProcessed & *m_pnTasksAll from external array }; +typedef boost::shared_ptr CTaskPtr; + /////////////////////////////////////////////////////////////////////////// // CProcessingException @@ -460,28 +466,29 @@ /////////////////////////////////////////////////////////////////////////// // CTaskArray -class CTaskArray : public CArray +class CTaskArray// : public CArray { public: CTaskArray(); ~CTaskArray(); void Create(chcore::IFeedbackHandlerFactory* piFeedbackHandlerFactory); - CTask* CreateTask(); + CTaskPtr CreateTask(); - size_t GetSize( ); - size_t GetUpperBound( ); - void SetSize(size_t stNewSize, int nGrowBy = -1); + size_t GetSize(); - CTask* GetAt(size_t stIndex); - size_t Add(CTask* newElement); + CTaskPtr GetAt(size_t stIndex); + CTaskPtr GetTaskBySessionUniqueID(size_t stSessionUniqueID); + size_t Add(const CTaskPtr& spNewTask); void RemoveAt(size_t stIndex, size_t stCount = 1); void RemoveAll(); void RemoveAllFinished(); - void RemoveFinished(CTask** pSelTask); + void RemoveFinished(const CTaskPtr& spSelTask); + void StopAllTasks(); + void SaveData(); void SaveProgress(); void LoadDataProgress(); @@ -515,6 +522,10 @@ CCriticalSection m_cs; TASK_CREATE_DATA m_tcd; +private: + std::vector m_vTasks; + size_t m_stNextSessionUniqueID; + protected: chcore::IFeedbackHandlerFactory* m_piFeedbackFactory; };