Um portátil e simples equivalente do Windows' e/S Sobreposta ReadFile

Eu estou lutando para porta de um pedaço de código para a leitura de arquivos de forma assíncrona no Windows, usando e/S sobreposta com ReadFileEx() e uma estrutura herdada do OVERLAPPED struct (para adicionar algumas variáveis e o CompletionRoutine de chamada de retorno). Não utilizar especial de API do Win32 truques ou algo do tipo, a única coisa que ele está sendo chamado como um WorkQueue a partir de um pool de threads.

std::weak_ptr<AsyncLoadOperation> weakToThis = op;
pool.Enqueue(
    [weakToThis]()
    {
        auto thisOp = weakToThis.lock();
        // if all other references to this object have been released
        // then the weak_ptr::lock() will fail, and we can consider
        // it a cancel
        if (!thisOp) return;

        // File Operations Start Here!

        // if we got to this point, we cannot cancel until the load
        // level read operation has been completed
        auto h = CreateFileA(
            (const char*)thisOp._naturalName.c_str(), GENERIC_READ, FILE_SHARE_READ,
            nullptr, OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
            nullptr);

        if (h == INVALID_HANDLE_VALUE) {
            // failed to load the file -- probably because it's missing
            thisOp->OnFailure();
            return;
        }

        auto fileSize = GetFileSize(h, nullptr);
        if (!fileSize || fileSize == INVALID_FILE_SIZE) {
            CloseHandle(h);
            thisOp->OnFailure();
            return;
        }

        thisOp->_buffer.reset((uint8*)MemAlign(fileSize, 16));
        thisOp->_bufferLength = fileSize;

        thisOp->_overlapped = std::make_unique<SpecialOverlapped>();
        XlSetMemory(thisOp->_overlapped.get(), 0, sizeof(OVERLAPPED));
        thisOp->_overlapped->_fileHandle = INVALID_HANDLE_VALUE;
        thisOp->_overlapped->_returnPointer = thisOp;

        auto readResult = ReadFileEx(
            h, thisOp->_buffer.get(), fileSize, 
            thisOp->_overlapped.get(), &SpecialOverlapped::CompletionRoutine);
        if (!readResult) {
            CloseHandle(h);
            thisOp->_overlapped->_returnPointer.reset();
            thisOp->OnFailure();
            return;
        }

        thisOp->_overlapped->_fileHandle = h;

    }
);

A rotina de conclusão define apenas o já cheio de memórias intermédias de dados a partir do arquivo de volta para a classe principal.

Eu só quero saber se existe um genérico/versão portátil deste, utilizando o outro de reposição thread para fazer a operação de leitura, usando o C++ threading bibliotecas, etc.

0
2019-09-18 20:17:23
origem
0 respostas

Veja mais perguntas por marcas