AIO als solches ist immer noch etwas begrenzt und ein echter Schmerz, um damit anzufangen, aber es funktioniert zum größten Teil, wenn Sie erst einmal durchgegraben haben.
Es hat einige meiner Meinung nach gravierenden Fehlern, aber das ist wirklich gehört. Wenn Sie beispielsweise eine bestimmte Anzahl von Befehlen oder Daten senden, wird Ihr übersetzender Thread blockiert. Ich erinnere mich nicht die genaue Begründung für diese Funktion, aber die Antwort, die ich zurück bekam dann war so etwas wie „Ja natürlich, die Kernel eine Begrenzung seiner Warteschlange Größe hat, dass beabsichtigt ist“. Was ist akzeptabel, wenn Sie ein paar tausend Anfragen einreichen ... offensichtlich muss irgendwo ein Limit sein. Dies könnte auch unter DoS-Gesichtspunkten sinnvoll sein (andernfalls könnte ein böswilliges Programm den Kernel dazu bringen, nicht genügend Arbeitsspeicher zu haben, indem es eine Milliarde Anfragen sendet). Aber es ist immer noch etwas, das Sie realistisch mit "normalen" Zahlen (etwa hundert) treffen können und es wird Sie unerwartet treffen, was nicht gut ist.Wenn Sie nur ein halbes Dutzend Anfragen einreichen und diese ein wenig größer sind (einige Megabyte an Daten), kann das gleiche passieren, anscheinend weil der Kernel sie in Unteranforderungen aufteilt. Was wiederum sinnvoll ist, aber wenn man sieht, wie die Docs es nicht sagen, sollte man erwarten, dass es keinen Unterschied macht (abgesehen davon, dass man länger braucht), ob man 500 Bytes oder 50 Megabyte Daten liest.
Es scheint auch keine Möglichkeit gepuffertes AIO zu geben, zumindest auf keinem meiner Debian- und Ubuntu-Systeme (obwohl ich andere Leute über das genaue Gegenteil klagen gesehen habe, dh ungepufferte Schreibvorgänge, die tatsächlich über die Puffer laufen). Von dem, was ich auf meinen Systemen sehen kann, ist AIO nur wirklich asynchron mit deaktivierter Pufferung, was eine Schande ist (deshalb verwende ich momentan ein hässliches Konstrukt um Speicherabbildung und einen Worker Thread).
Ein wichtiges Problem bei etwas Asynchronem ist es, epoll_wait() darauf zu setzen, was wichtig ist, wenn Sie etwas anderes machen, abgesehen von der Festplatten-IO (wie das Empfangen von Netzwerkverkehr). Natürlich gibt es io_getevents, aber es ist nicht so wünschenswert/nützlich, da es nur für eine einzige Sache funktioniert.
In den letzten Kernen gibt es Unterstützung für eventfd. Auf den ersten Blick erscheint es nutzlos, da es nicht offensichtlich ist, wie es in irgendeiner Weise hilfreich sein könnte. Doch zu Ihrer Rettung gibt es die undokumentierte Funktion io_set_eventfd, mit der Sie AIO mit einer eventfd verknüpfen können, die epoll_wait() - fähig ist. Sie müssen durch die Header graben, um es herauszufinden, aber es ist sicherlich da, und es funktioniert gut.
Mm, vielleicht solltest du deinen Flammenanzug anziehen und nach LKML fragen. – ninjalj
siehe http://blog.libtorrent.org/2012/10/asynchronous-disk-io/ –