Ich versuche Windows überlappen IO, aber ich kann nicht scheinen, es asynchron zu arbeiten. Ich habe das Programm kompiliert und ausgeführt, aber es druckt nie etwas, es wird nur leise abgeschlossen. Ich habe gelesen, dass kleine Lesevorgänge synchron werden könnten, deshalb habe ich mich bewusst dafür entschieden, 512 MB zu lesen.Windows überlappt IO blockiert tatsächlich
const DWORD Size = 1<<29; // 512MB
char* Buffer = (char*)malloc(Size);
DWORD BytesRead;
OVERLAPPED Overlapped;
memset(&Overlapped, 0, sizeof(Overlapped));
HANDLE File = CreateFile("BigFile", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL|FILE_FLAG_OVERLAPPED, NULL);
assert(File!=INVALID_HANDLE_VALUE);
DWORD Result = ReadFileEx(File, Buffer, Size, &Overlapped, NULL); // This line takes 150ms according to the debugger
assert(Result);
while(!GetOverlappedResult(File, &Overlapped, &BytesRead, FALSE)) {
printf("Waiting...\n");
}
Als zusätzliche Information, habe ich den Code in den Debugger tritt, und der Overlapped.InternalHigh
Wert aktualisiert wird (mit dem gleichen Wert wie Size
) während des ReadFileEx
Anrufs.
Ich habe versucht, malloc
mit VirtualAlloc
, ReadFileEx
mit ReadFile
ersetzen, das Hinzufügen FILE_FLAG_NO_BUFFERING
, und überprüft, dass die Rückkehr von ReadFile
0 war und dass GetLastError
wäre ERROR_IO_PENDING
nach dem Lesen. Ich habe versucht, mit RAMMap zu sehen, ob die Datei im Cache war, aber nur 96KB davon war da.
Ich verwende Windows 10 (Version 1703) mit 8 GB RAM.
Vielleicht ist die Datei durch das Betriebssystem zwischengespeichert wird, so dass das Betriebssystem entscheidet, dass es leicht die sofort lesen bedienen kann ? – EOF
@EOF Würde es ernsthaft eine ganze 512MB + Datei zwischenspeichern? Plus, wenn es zwischengespeichert wird, dauert mein Lesen immer noch 150ms ... was ist dann der Punkt der Überlappung, wenn es mir keine schnelle Rückkehr garantieren kann? – Lutopia
Dies ist wirklich Cache bezogen. Öffnen Sie die Datei mit 'FILE_FLAG_OVERLAPPED | FILE_FLAG_NO_BUFFERING' und weisen Sie' PVOID Buffer = VirtualAlloc (0, Size, MEM_COMMIT, PAGE_READWRITE) 'zu (es muss für nicht zwischengespeicherte Lesevorgänge ausgerichtet sein) - und prüfen Sie das Ergebnis. und in deinem Fall besser 'ReadFile' verwenden (ohne' Ex') - es wird in diesem Fall mit dem letzten Fehler zu dir zurückkehren - 'ERROR_IO_PENDING' – RbMm