Вы можете отменить синхронный ввод/вывод (I/O) данных из любого потока в процессе, который запустил операцию ввода/вывода. Вы должны определить дескриптор потока, который, осуществлял операцию текущего ввода - вывода (I/O).
Пример ниже показывает две процедуры:
|
Дополнительные инструкции по проверкам, которые, не включаются здесь, требуются в процедуре SynchronousIoWorker для гарантии того, что, если отмена запрашивалась в ходе коротких периодов между вызовами файлового ввода-вывода (I/O), то оставшаяся часть операции должна быть отмененной.
DWORD gCompletionStatus; // Статус завершения для последней операции
DWORD dwOperationInProgress; // TRUE, если операция выполняется
VOID
SynchronousIoWorker( VOID * pv )
{
LPCSTR lpFileName = (LPCSTR) *pv;
HANDLE hEvent = lpCreateParams->hEvent;
HANDLE hFile;
dwOperationInProgress = TRUE;
gCompletionStatus = ERROR_SUCCESS;
hFile = CreateFileA(lpFileName,
GENERIC_READ,
0,
NULL,
OPEN_EXISTING,
0,
NULL);
if (hFile != INVALID_HANDLE_VALUE)
{
// TODO: CreateFile завершилась успешно.
// Вставьте свой код, чтобы сделать больше синхронных вызовов с hFile.
if (result == FALSE)
{
// Операция завершалась ошибкой или была отменена. Если она была отменена,
// GetLastError() возвратит ERROR_OPERATION_ABORTED.
gCompletionStatus = GetLastError();
}
CloseHandle(hFile);
} else
{
// CreateFile завершалась ошибкой или была отменена. Если она была отменена,
// GetLastError() возвратит ERROR_OPERATION_ABORTED.
gCompletionStatus = GetLastError();
}
dwOperationInProgress = FALSE;
} // Конец SynchronousIoWorker( )
//--------------------------------------------------------
LRESULT
CALLBACK
MainUIThreadMessageHandler(HWND hwnd,
UINT uMsg,
WPARAM wParam,
LPARAM lParam)
{
HANDLE syncThread;
// Вставьте свои инициализации здесь.
switch (uMsg)
{
// Пользователь запросил операцию на файле. Вставьте свой код,
// чтобы извлечь имя файла из параметров.
case WM_MYSYNCOPS:
syncThread = CreateThread(
NULL,
0,
(LPTHREAD_START_ROUTINE)SynchronousIoWorker,
&lpFileName,
0,
NULL);
if (syncThread == INVALID_HANDLE_VALUE)
{
// Вставьте свой код, чтобы обработать сбой.
}
break;
// Пользователь щелкнул по кнопке отмены.
case WM_MYCANCEL:
if (syncThread != INVALID_HANDLE_VALUE)
{
CancelSynchronousIo(syncThread);
}
break;
// Пользователь затребовал другую операцию.
case WM_PROCESSDATA:
if (!dwOperationInProgress)
{
if (gCompletionStatus == ERROR_OPERATION_ABORTED)
{
// Вставьте свой код очистки здесь.
} else if (...)
{
// Вставьте код обработки других случаев.
}
}
break;
} // Конец switch (uMsg)
return TRUE;
} // Конец MainUIThreadMessageHandler( )
|