Asynchronous windows I/O ( Overlapped I/O )

>> Sunday, October 18, 2009

You may check the artical : "TransmitFile internal" for understanding the use of asynchronous operations on socket.

Now it's time to clear out something. And i think after reading this artical, you can go through other codes about asychronous I/O without problems.
Remember that, in windows, asynchronous I/O is also called overlapped I/O.
To use asynchronous I/O operations, the functions are ReadFile and WriteFile , but the file needs to be opened in the mode FILE_FLAG_OVERLAPPED.
Now there is a question: How can thread knows about the completion of I/O operations ?
The answer is : Use an event descriptor.
This is the format of structure OVERLAPPED.

typedef struct _OVERLAPPED
{
  DWORD Internal; // reserved
  DWORD InternalHigh; // reserved
  DWORD Offset;
  DWORD OffsetHigh;
  HANDLE hEvent;
} OVERLAPPED,  *LPOVERLAPPED;

The fields Offset and OffsetHigh indicate low part and high part of the offset according to the beggining of the file. From this offset, operating system begins run the asynchronous operations.
Parameter hEvent is used by thread for the completion of I/O operations.
OK, let's go to the codes: Writing 0 to 10 to file demo.dat
#include <windows.h>

using namespace std;
int main()
{
  HANDLE hFile;
  HANDLE hEndWrite; // event
  OVERLAPPED ovl;
  hEndWrite = CreateEvent(NULL, FALSE, FALSE, NULL);

  ovl = 
{
    0, 0, 0, 0, hEvent
};

  hFile = CreateFile("C:\\demo.dat", GENERIC_WRITE, FILE_SHARE_WRITE, NULL,
    OPEN_ALWAYS, FILE_FLAG_OVERLAPPED, NULL);

  // write to file

  for (int i = 0; i < 10; ++i)
  {
    DWORD dwBytesWritten;
    DWORD ret;
    WriteFile(hFile, &i, sizeof(i), &dwBytesWritten, &ovl);
    WaitForSingleObject(hEndWrite, INFINITE);
    ovl.Offset += sizeof(i);
  }

  CloseHandle(hFile);
  CloseHandle(hEndWrite);

  return 0;
}



0 comments: