Ottimizzazione TCP per le prestazioni della rete


Questa pagina illustra i metodi per calcolare le impostazioni corrette per ridurre la latenza delle connessioni TCP in Google Cloud e negli scenari ibridi. Questa pagina ti aiuta anche a capire come migliorare la latenza della connessione tra i processi in Google Cloud.

L'architettura moderna dei microservizi sostiene che gli sviluppatori debbano creare piccoli servizi con responsabilità singola. I servizi devono comunicare utilizzando TCP o UDP, in base alle aspettative di affidabilità del sistema. È quindi fondamentale che i sistemi basati su microservizi comunichino in modo affidabile e con bassa latenza.

Google Cloud offre affidabilità e bassa latenza grazie a una rete globale, il che significa che anche gli utenti della tua applicazione possono operare a livello globale. Avere una rete globale significa creare una rete Virtual Private Cloud (VPC) che si estenda su regioni e zone. Le applicazioni possono connettersi tra loro in regioni e zone diverse senza mai uscire dalla rete Google Cloud.

Le applicazioni scritte per un ambiente di data center tradizionale possono avere un rendimento lento quando vengono spostate in un ambiente cloud ibrido, ovvero quando alcuni componenti dell'applicazione vengono eseguiti in un data center aziendale e altri nel cloud. Le prestazioni lente possono essere il risultato di diversi fattori. Questo articolo si concentra sulle latenze di andata e ritorno e su come la latenza influisce sulle prestazioni del protocollo TCP nelle applicazioni che spostano una quantità considerevole di dati su qualsiasi parte della rete.

Il problema: latenza e comportamento TCP

TCP utilizza un meccanismo di gestione delle finestre per impedire a un mittente veloce di superare un ricevente lento. Il destinatario indica la quantità di dati che il mittente deve inviare prima di dover attendere un aggiornamento della finestra da parte del destinatario. Di conseguenza, se un'applicazione di ricezione non può ricevere dati sulla connessione, esiste un limite alla quantità di dati che possono essere messi in coda in attesa dell'applicazione.

La finestra TCP consente un utilizzo efficiente della memoria sui sistemi di invio e ricezione. Man mano che l'applicazione di ricezione consuma dati, gli aggiornamenti della finestra vengono inviati al mittente. L'aggiornamento della finestra può avvenire più rapidamente in un solo viaggio di andata e ritorno, che porta alla seguente formula per uno dei limiti alle prestazioni del trasferimento collettivo di una connessione TCP:

Throughput <= dimensione finestra / latenza tempo di round trip (RTT)

Nel progetto originale per TCP, questa finestra ha una dimensione massima di 65535 byte (64 KiB - 1). Si tratta della quantità massima di dati che il mittente poteva inviare prima di ricevere un aggiornamento della finestra per consentire l'invio di più dati.

Modifiche al protocollo TCP dalla sua introduzione

Da quando è stato introdotto il protocollo TCP, alcune funzionalità chiave sono cambiate:

  • Le velocità di rete tipiche sono aumentate di quattro ordini di grandezza.
  • La memoria tipica di un sistema è aumentata di quattro ordini di grandezza.

Il risultato della prima modifica è che le dimensioni delle finestre TCP originali hanno comportato un uso inefficiente delle risorse di rete. Un mittente invia una finestra di dati alla massima velocità possibile in base alle condizioni di rete, quindi rimane inattivo per un periodo di tempo considerevole in attesa dell'aggiornamento della finestra TCP. Il risultato della seconda modifica è che mittenti e destinatari possono utilizzare più memoria per la rete per risolvere la limitazione esposta dalla prima modifica.

Il seguente diagramma illustra questo interscambio.

Il mittente invia solo 64 KB di dati e attende molto tempo dopo l&#39;invio prima di ricevere un aggiornamento della finestra

Il mittente non può utilizzare completamente la rete perché è in attesa dell'aggiornamento della finestra TCP prima di inviare dati aggiuntivi.

Invio di più dati alla volta

La soluzione è inviare più dati alla volta. Man mano che la larghezza di banda della rete aumenta, più dati possono essere inseriti nel canale (rete) e, man mano che il canale si allunga, ci vuole più tempo per confermare la ricezione dei dati. Questa relazione è nota come prodotto larghezza di banda-ritardo (BDP). Viene calcolato come larghezza di banda moltiplicata per il tempo di round trip (RTT), ottenendo un valore che specifica il numero ottimale di bit da inviare per riempire il canale. La formula è la seguente:

BDP (bit) = larghezza di banda (bit/s) * RTT (secondi)

Il BDP calcolato viene utilizzato come dimensione della finestra TCP per l'ottimizzazione.

Ad esempio, immagina di avere una rete da 10 Gbps con un RTT di 30 millesecondi. Per la dimensione della finestra, utilizza il valore della dimensione della finestra TCP originale (65535 byte). Questo valore non assomiglia nemmeno a sfruttare la capacità di larghezza di banda. Le prestazioni TCP massime possibili su questo link sono come segue:

(65535 byte * 8 bit/byte) = larghezza di banda * 0,030 secondi
larghezza di banda = (65535 byte * 8 bit/byte) / 0,030 secondi
larghezza di banda = 524280 bit / 0,030 secondi
larghezza di banda = 17476000 bit / secondo

In altre parole, questi valori generano un throughput leggermente superiore ai 17 Mbit al secondo, ovvero una piccola frazione della capacità di 10 Gbps della rete.

La soluzione: ridimensionamento della finestra TCP

Per risolvere le limitazioni delle prestazioni imposte dal design originale della dimensione della finestra TCP, sono state introdotte estensioni al protocollo TCP che consentono di scalare la dimensione della finestra a valori molto più grandi. La scalabilità delle finestre supporta finestre fino a 1.073.725.440 byte, ovvero quasi 1 GB. Questa funzionalità è descritta nel RFC 7323 come opzione di scala della finestra TCP.

Le estensioni di scala della finestra espandono la definizione della finestra TCP in modo da utilizzare 30 bit e poi utilizzano un fattore di scala implicito per trasportare questo valore di 30 bit nel campo della finestra di 16 bit dell'intestazione TCP. Per verificare se la funzionalità è abilitata sui sistemi basati su Linux, utilizza il seguente comando:

sudo sysctl net.ipv4.tcp_window_scaling

Questa funzionalità è attivata per impostazione predefinita su tutte le macchine virtuali Linux di Google Cloud. Se viene restituito un valore 1, significa che l'opzione è attivata. Se la funzionalità è disattivata, puoi attivarla utilizzando il seguente comando:

sudo sysctl -w net.ipv4.tcp_window_scaling=1

Throughput con una dimensione della finestra più grande

Puoi utilizzare l'esempio precedente per mostrare il vantaggio della scalabilità della finestra. Come prima, ipotizza una rete da 10 Gbps con una latenza di 30 millisecondi, quindi calcola una nuova dimensione della finestra utilizzando questa formula:

(Velocità di collegamento * latenza) / 8 bit = dimensioni finestra

Se inserisci i numeri di esempio, ottieni quanto segue:

(10 Gbps * 30 ms/1000 sec) / 8 bit/byte = dimensione finestra
(10000 Mbps * 0,030 secondi) / 8 bit/byte = 37,5 MB

L'aumento della dimensione della finestra TCP a 37 MB può aumentare il limite teorico delle prestazioni del trasferimento collettivo TCP a un valore che si avvicina alla capacità della rete. Naturalmente, molti altri fattori possono limitare il rendimento, tra cui il sovraccarico del sistema, le dimensioni medie dei pacchetti e il numero di altri flussi che condividono il link, ma come puoi vedere, le dimensioni della finestra riducono notevolmente i limiti imposti dalle dimensioni della finestra limitata precedente.

Impostazione di parametri di Linux per modificare le dimensioni della finestra TCP

In Linux, la dimensione della finestra TCP è influenzata dai seguenti parametri sysctl(8) configurabili:

net.core.rmem_max
net.core.wmem_max
net.ipv4.tcp_rmem
net.ipv4.tcp_wmem

I primi due parametri di configurazione influiscono sulla dimensione massima della finestra TCP per le applicazioni che tentano di controllarla direttamente, limitando la richiesta delle applicazioni a non più di questi valori. I due parametri di configurazione successivi influiscono sulle dimensioni della finestra TCP per le applicazioni che consentono a Linux di eseguire l'ottimizzazione automatica.

Il valore ottimale della dimensione della finestra dipende dalle circostanze specifiche, ma un punto di partenza è il BDP (prodotto di larghezza di banda e tempo di latenza) più grande per il percorso o i percorsi su cui prevedi che il sistema invii i dati. In questo caso, devi impostare i parametri di ottimizzazione seguendo questi passaggi:

  1. Assicurati di disporre dei privilegi di root.
  2. Visualizza le impostazioni attuali del buffer. Salva queste impostazioni nel caso in cui tu voglia eseguire il rollback di queste modifiche.

    sudo sysctl -a | grep mem
    
  3. Imposta una variabile di ambiente con la nuova dimensione della finestra TCP che vuoi utilizzare:

    MaxExpectedPathBDP=8388608
    
  4. Imposta la dimensione massima del buffer di ricezione del sistema operativo per tutti i tipi di connessioni:

    sudo sysctl -w net.core.rmem_max=$MaxExpectedPathBDP
    
  5. Imposta la dimensione massima del buffer di invio del sistema operativo per tutti i tipi di connessioni:

    sudo sysctl -w net.core.wmem_max=$MaxExpectedPathBDP
    
  6. Imposta le impostazioni del buffer della memoria di ricezione TCP (tcp_rmem):

    sudo sysctl -w net.ipv4.tcp_rmem="4096 87380 $MaxExpectedPathBDP"
    

    L'impostazione tcp_rmem accetta tre valori:

    • La dimensione minima del buffer di ricezione che può essere allocata per una socket TCP. In questo esempio, il valore è 4096 byte.
    • La dimensione predefinita del buffer di ricezione, che sostituisce anche il valore /proc/sys/net/core/rmem_default utilizzato da altri protocolli. Nell'esempio, il valore è 87380 byte.
    • La dimensione massima del buffer di ricezione che può essere allocata per una socket TCP. Nell'esempio, è impostato sul valore impostato in precedenza (8388608 byte).
  7. Imposta le impostazioni del buffer di memoria di invio TCP (tcp_wmem):

    sudo sysctl -w net.ipv4.tcp_wmem="4096 16384 $MaxExpectedPathBDP"
    

    L'impostazione tcp_wmem accetta tre valori:

    • Lo spazio del buffer di invio TCP minimo disponibile per una singola socket TCP.
    • Lo spazio del buffer predefinito consentito per una singola socket TCP.
    • Lo spazio massimo del buffer di invio TCP.
  8. Imposta i parametri di configurazione in modo che le connessioni successive utilizzino i valori specificati:

    sudo sysctl -w net.ipv4.route.flush=1
    

Per mantenere queste impostazioni dopo i riavvii, aggiungi i comandi impostati precedentemente al file /etc/sysctl.conf:

sudo bash -c 'cat << EOF >> /etc/sysctl.conf
net.core.rmem_max=8388608
net.core.wmem_max=8388608
net.ipv4.tcp_rmem=4096 87380 8388608
net.ipv4.tcp_wmem=4096 16384 8388608
net.ipv4.route.flush=1
EOF'

Testare il tempo di risposta con una dimensione della finestra aggiornata

Quando il protocollo TCP ha una dimensione della finestra sufficientemente grande da utilizzare il BDP, il quadro cambia, come mostrato nel seguente diagramma:

Il mittente invia una grande quantità di dati alla volta e attende pochissimo tempo per l&#39;aggiornamento di una finestra

Le dimensioni della finestra TCP possono essere sempre adattate in base alle risorse disponibili per il processo interessato e all'algoritmo TCP in uso. Come mostra il diagramma, la scalabilità della finestra consente a una connessione di superare di gran lunga le dimensioni della finestra di 65 KiB definite nella specifica TCP originale.

Puoi testarlo tu stesso. Innanzitutto, assicurati di aver apportato modifiche alle dimensioni della finestra TCP sul computer locale e su un computer remoto impostando i parametri di configurazione su entrambe le macchine. Poi esegui i seguenti comandi:

dd if=/dev/urandom of=sample.txt bs=1M count=1024 iflag=fullblock
scp sample.txt your_username@remotehost.com:/some/remote/directory

Il primo comando crea un file sample.txt da 1 GB con dati casuali. Il secondo comando copia il file dalla macchina locale a una macchina remota.

Prendi nota dell'output comando scp nella console, che mostra la larghezza di banda in Kbps. Dovresti notare una differenza significativa nei risultati prima e dopo le modifiche delle dimensioni della finestra TCP.

Passaggi successivi