stats overloaded iowait iotop linux io

overloaded - monitoring disk io linux



Linux: cuándo usar dispersión/recopilar E/S(readv, writev) frente a un gran búfer con fread (1)

La conveniencia principal ofrecida por readv , writev es:

  1. Permite trabajar con bloques de datos no contiguos. es decir, los buffers no tienen que formar parte de una matriz, sino que deben asignarse por separado.
  2. La E / S es ''atómica''. es decir, si realiza una writev , todos los elementos del vector se escribirán en una operación contigua, y las escrituras realizadas por otros procesos no se producirán entre ellas.

Por ejemplo, digamos que sus datos están segmentados naturalmente y provienen de diferentes fuentes:

struct foo *my_foo; struct bar *my_bar; struct baz *my_baz; my_foo = get_my_foo(); my_bar = get_my_bar(); my_baz = get_my_baz();

Ahora, los tres ''buffers'' no son un gran bloque contiguo. Pero desea escribirlos contiguamente en un archivo, por cualquier motivo (por ejemplo, son campos en el encabezado de un archivo para un formato de archivo).

Si usas write tienes que elegir entre:

  1. Copiándolos en un bloque de memoria usando, por ejemplo, memcpy (sobrecarga), seguido de una sola llamada de write . Entonces la escritura será atómica.
  2. Hacer tres llamadas separadas para write (gastos generales). Además, las llamadas de write de otros procesos pueden intercalarse entre estas escrituras (no atómicas).

Si usas writev en su lugar, todo está bien:

  1. Usted hace exactamente una llamada al sistema, y ​​no hay memcpy para hacer un solo búfer de los tres.
  2. Además, los tres búferes se escriben atómicamente, como escritura de un bloque. es decir, si otros procesos también escriben, entonces estas escrituras no aparecerán entre las escrituras de los tres vectores.

Entonces harías algo como:

struct iovec iov[3]; iov[0].iov_base = my_foo; iov[0].iov_len = sizeof (struct foo); iov[1].iov_base = my_bar; iov[1].iov_len = sizeof (struct bar); iov[2].iov_base = my_baz; iov[2].iov_len = sizeof (struct baz); bytes_written = writev (fd, iov, 3);

Fuentes:

  1. http://pubs.opengroup.org/onlinepubs/009604499/functions/writev.html
  2. http://linux.die.net/man/2/readv

En dispersión y recopilación (es decir, readv y writev ), Linux lee en múltiples buffers y escribe desde múltiples buffers.

Por ejemplo, si tengo un vector de 3 buffers, puedo usar readv , O puedo usar un solo buffer, que es de un tamaño combinado de 3 buffers y hago fread .

Por lo tanto, estoy confundido: ¿para qué casos se debe utilizar la dispersión / recopilación y cuándo se debe usar un solo búfer grande?