2011-11-23 21 views
6

Quanto è grande (approssimativamente) un overhead di I/O syscall su Linux dal programma C, intendo quanto è male in esecuzione, ad es. molte piccole operazioni read/write rispetto a read/write su buffer di grandi dimensioni (su file regolari o socket di rete)? L'app è fortemente multithread.Overhead di Syscall

+5

Il 20% è cattivo. Qual è la tua metrica sulle prestazioni? –

+1

I/O è in genere una delle parti, se non le, più lente di un programma. –

+0

@GregHewgill, per la maggior parte delle persone usa il tempo. Per esempio. è cattivo 2ms. Suppongo che ci sia un dibattito esistenziale sulla natura del tempo, ma è quello che userò. –

risposta

14

Syscollere almeno 1-2 microsecondi sulla maggior parte delle macchine moderne solo per l'overhead di syscall e molto più tempo se stanno facendo qualcosa di complesso che potrebbe bloccare o dormire. Aspettatevi almeno 20 microsecondi e fino all'ordine dei millisecondi per l'IO. Confrontalo con una minuscola chiamata di funzione o macro che legge un byte da un buffer dello spazio utente, che probabilmente completerà in una questione di nanosecondi (forse 200 ns in una brutta giornata).

+4

+1, grazie per non essere tutti mistici e nichilisti su problemi di prestazioni come tanti. –

+0

Sì, non è il sovraccarico di 'syscall' di cui ti devi preoccupare - è il lavoro che la chiamata di sistema fa è lenta! – Gabe

+2

@Gabe: Non è del tutto così semplice, almeno non in tutti i casi. Per eseguire l'IO effettivo, il lavoro è moderatamente costoso, ma per il multiplexing IO ('select'), i tempi (' nanosleep'), il controllo del segnale ('sigprocmask'), gli oggetti di sincronizzazione (' futex') e molti altri casi, il tempo complessivo è in realtà dominato dall'overhead di syscall e non dal lavoro svolto. Infatti, per molti scopi, il fattore costante dall'overhead di syscall è talmente ampio che è pratico contare solo le syscall (cioè considerare tutto il resto 'O (0)') nel capire come il tempo si ridimensiona con i dati della dimensione del mondo reale. –

3

È possibile misurare da soli. Basta aprire /dev/zero e fare un po 'di lettura e scrittura durante la misurazione del tempo. Inoltre, varia il numero di byte che inserisci in ogni chiamata, ad es. 1 byte, 2 byte, 128 byte, 4096 byte. Prestare inoltre attenzione a utilizzare le scale di sistema read(2) e write(2) e non utilizzare alcun buffer interno.

+0

Sebbene questa sia una buona idea, '/ dev/zero' non include alcun I/O effettivo, quindi potrebbe non fornire risposte accurate. – Gabe

+1

@Gabe: Questo è esattamente il punto. James voleva sapere l'overhead I/O _syscall_, non il tempo per il trasferimento effettivo dei dati ai dischi. Effettuare l'I/O su un dispositivo a blocchi basato su RAM fornisce un'approssimazione molto buona di questo sovraccarico. –

+0

Per illustrare il mio punto, se si eseguono molte scritture su un socket di rete, si potrebbero inviare molti piccoli pacchetti piuttosto che meno grandi. Ciò potrebbe causare congestione sulla rete e rallentare le cose. Se così fosse, non lo scopriresti mai semplicemente scrivendo a/dev/zero. – Gabe