Explorant io_uring: com Linux accelera les operacions d’entrada/sortida moderna

Una de les principals innovacions al kernel de Linux és io_uring (introduït a la versió 5.1 del kernel). És una nova API relacionada amb les operacions d’I/O, optimitzant-ne enormement el seu rendiment.

En aquest post explicarem què és io_uring, com funciona internament, i quins avantatges tècnics aporta respecte a mecanismes clàssics.

io_uring és una interfície d’I/O basada en ring buffers compartits entre espai d’usuari i de kernel. Això permet als programes realitzar operacions d’entrada/sortida fent menys entrades al kernel i, sovint, reduint també canvis de context (millorant la latència i el consum de CPU).

Els mecanismes d’I/O més antics tenen limitacions:

  • Sincrònics: Els processos queden bloquejats.

  • Cada operació implica una syscall (afegint sobrecàrrega).

  • Poc consistent i incompleta.

  • No suporta totes les operacions.

  • Implementació complicada i lenta.

Excel·lent per sockets, però amb fitxers normals no pot notificar esdeveniments I/O.

Requereix syscalls.

io_uring conté dos ring buffers en memòria compartida:

  • Submission queue

    Aquest és el ring buffer on les aplicacions envien les peticions I/O.

  • Completion queue

    Quan el kernel acaba l’operació, envia el resultat aquí, llesta per al programa.

io_uring només necessita dues syscalls per configurar la interfície:

io_uring_setup() i io_uring_enter() per empènyer entrades quan és necessari.

La resta de comunicacions passa pel buffer de memòria compartida, sense syscalls per cada petició.

A més, amb el mode SQPOLL, el kernel dedica un thread per processar peticions sense que l’usuari faci syscalls, reduint la sobrecàrrega.

  • Syscalls reduides

    La major part de la feina es fa en memòria compartida, pel que reduim els canvis de context.

  • Menor latència

    Comparat amb altres mètodes, ofereix una latència molt menor.

  • Operacions unificades

    Permet diverses operacions, com:

    • Fitxers

    • Sockets

    • Pipes

    • BPF

  • Zero-copy

    io_uring suporta operacions zero-copy (veure aquí) en sockets i altres operacions específiques, reduint còpies de dades innecessàries.

  • Disseny escalable

    Està pensat per escalar multicore, amb una capacitat de paral·lelisme enorme.

io_uring és de les innovacions més importants dels últims anys. Amb la seva arquitectura de memòria compartida i minimitzant les syscalls, dóna un rendiment molt superior a aplicacions que requereixen moltes peticions I/O.

I fins aquí el post d’avui. Si t’ha semblat útil pots deixar un comentari i compartir-lo. Ens veiem al següent!