2010-10-11 13 views
10

Lo pido aquí, ya que Google lo guía en un viaje feliz por los archivos sin ninguna pista sobre cuál es el estado actual. Si vas por Google, parece que Async IO estuvo de moda entre 2001 y 2003, y para 2006 algunas cosas como epoll y libaio estaban apareciendo; kevent apareció pero parece haber desaparecido, y hasta donde puedo decir, todavía no hay buena forma de mezclar basada en terminación y señalización basada en listo, asincrónico sendfile - ¿eso es posible? y todo lo demás en un ciclo de eventos de subproceso único.El estado de Linux async IO?

Así que por favor dime que estoy equivocado y ¡todo es color de rosa! y, lo que es más importante, qué API usar.

¿Cómo se compara Linux con FreeBSD y otros sistemas operativos en este sentido?

+3

Mm, tal vez deberías poner tu traje de llama y preguntar por LKML. – ninjalj

+1

ver http://blog.libtorrent.org/2012/10/asynchronous-disk-io/ –

Respuesta

3

El disco asíncrono IO está vivo y coleando ... en realidad es compatible y funciona razonablemente bien ahora, pero tiene limitaciones importantes (pero con suficiente funcionalidad que algunos de los usuarios más importantes pueden usarlo, por ejemplo, Innodb de MySQL lo hace en la última versión).

El disco asíncrono IO es la capacidad de invocar las operaciones de IO de disco de forma no bloqueante (en un solo hilo) y esperar a que se completen. Esto funciona bien, http://lse.sourceforge.net/io/aio.html tiene más información.

AIO hace lo suficiente para que una aplicación típica (servidor de base de datos) pueda usarlo. AIO es una buena alternativa para crear muchos subprocesos haciendo IO síncrono, o usar scatter/gather en la familia preadv de llamadas al sistema que ahora existen.

Es posible hacer un trabajo IO sincrónico de "lista de compras" utilizando la nueva llamada preadvertida en la que el kernel irá y obtendrá un grupo de páginas de diferentes desplazamientos en un archivo. Esto está bien siempre que solo tenga un archivo para leer. (NB: existe la función de escritura equivalente).

encuesta, epoll, etc., son solo formas sofisticadas de hacer selec() que presentan menos limitaciones y problemas de escalabilidad, es posible que no se puedan mezclar fácilmente con el disco, pero en una aplicación del mundo real, puede probablemente evite esto de forma bastante trivial mediante el uso de subprocesos (algunos servidores de bases de datos tienden a hacer este tipo de operaciones en subprocesos separados de todos modos). Poll() es bueno, epoll es mejor, para grandes cantidades de descriptores de archivos. select() también está bien para números pequeños de descriptores de archivos (o específicamente, números bajos de descriptores de archivos).

+0

¿dónde está esto? http://stackoverflow.com/questions/1825621/how-do-you-use-aio-and-epoll-together-in-a-single-event-loop – Will

+0

(pensé que las encuestas y select eran simétricas y O (n), mientras que epoll es O (1) – Will

+0

encuesta es mejor que seleccionar porque funciona mucho mejor con un conjunto escaso de descriptores de archivos; digamos que desea sondear 10 FD de 10000 abiertos, no necesita una matriz de 10000 entradas que se inicializarán con ceros. Epoll es mejor porque solo necesita registrar los nuevos FD que le interesan, no pasar todos los que ya estaba viendo. – MarkR

2

La mayor parte de lo que aprendí sobre las E/S asincrónicas en Linux fue trabajando en la fuente Lighttpd. Es un servidor web de subproceso único que maneja muchas conexiones simultáneas, utilizando lo que cree que es lo mejor de los mecanismos de E/S asíncronas disponibles en el sistema en ejecución. Echa un vistazo a la fuente, es compatible con Linux, BSD y (creo) algunos otros sistemas operativos.

4

AIO como tal todavía es un tanto limitado y un verdadero dolor para comenzar, pero funciona en su mayor parte, una vez que lo has buscado.

Tiene algunos en mi opinión errores serios, pero esas son realmente características. Por ejemplo, al enviar una cierta cantidad de comandos o datos, se bloqueará el envío de subprocesos. No recuerdo la justificación exacta de esta característica, pero la respuesta que obtuve en ese momento fue algo así como "sí, por supuesto, el núcleo tiene un límite en el tamaño de la cola, eso es lo que se esperaba". Lo cual es aceptable si envía unas miles de solicitudes ... obviamente, tiene que haber un límite en alguna parte. También podría tener sentido desde el punto de vista de DoS (de lo contrario, un programa malicioso podría obligar al kernel a quedarse sin memoria publicando mil millones de solicitudes). Pero aún así, es algo que puedes enfrentar de manera realista con números "normales" (un centenar o más) y te sorprenderá inesperadamente, lo cual no es bueno.Además, si solo envía media docena de solicitudes y son un poco más grandes (algunos megabytes de datos), puede suceder lo mismo, aparentemente porque el kernel las divide en subpeticiones. Lo cual, una vez más, tiene algún sentido, pero al ver cómo los documentos no lo dicen, uno debe esperar que no haga ninguna diferencia (aparte de tomar más tiempo) si lee 500 bytes o 50 megabytes de datos.

Además, parece que no hay forma de hacer AIO con búfer, al menos en cualquiera de mis sistemas Debian y Ubuntu (aunque he visto a otras personas quejarse de todo lo contrario, es decir, grabaciones sin búfer de hecho pasando por los buffers) Según lo que puedo ver en mis sistemas, AIO solo está realmente asíncrono con el almacenamiento en búfer desactivado, lo cual es una pena (es por eso que actualmente estoy usando una construcción fea alrededor de la asignación de memoria y una hebra de trabajo).

Un problema importante con cualquier elemento asíncrono es poder hacer epoll_wait() en él, lo cual es importante si está haciendo algo más aparte del disco IO (como recibir tráfico de red). Por supuesto, hay io_getevents, pero no es tan deseable/útil, ya que solo funciona para una cosa singular.

En kernels recientes, hay soporte para eventfd. A primera vista, parece inútil, ya que no es obvio cómo puede ser útil de ninguna manera. Sin embargo, para su rescate, existe la función no documentada io_set_eventfd que le permite asociar AIO con un eventfd, que es epoll_wait() - able. Tienes que buscar en los encabezados para descubrirlo, pero ciertamente está ahí, y funciona muy bien.

+0

supongo que esto se refiere a Kernel AIO en lugar de POSIX AIO? –

+1

@JanusTroelsen: Sí, al igual que la pregunta, esto se refiere a kernel AIO ('libaio'). POSIX AIO no es tanto una característica de Linux, sino una función de biblioteca implementada en' librt' utilizando un grupo de subprocesos y síncrono estándar I/O. Sorprendentemente, esto funciona ** mucho ** mejor que el kernel im plementación, en todos los aspectos. – Damon

Cuestiones relacionadas