Su Linux, come posso sapere quante porte effimere sono rimaste disponibili?


17

Esiste un metodo in Linux per verificare quante porte effimere rimangono disponibili? Di tanto in tanto vedo errori "Indirizzo già in uso" a causa dell'esaurimento delle porte temporanee. Un riavvio automatico risolverà questo problema, ma sarebbe meglio prenderlo prima che accada.


Se si verificano errori del genere, suggerirei che o stai abusando del sistema non utilizzando il software o l'architettura giusti per un lavoro, oppure il tuo software si sta comportando male o non è configurato correttamente. Forse i tuoi timeout sono troppo lunghi per la tua applicazione o qualcosa sta lasciando le connessioni aperte senza usarle?
Caleb,

1
Esistono molte applicazioni valide che richiedono porte effimere aggiuntive oltre alle impostazioni predefinite del sistema operativo.
GregB,

Risposte:


26

L'intervallo di porte ephermal è specificato in /proc/sys/net/ipv4/ip_local_port_range. Probabilmente puoi estenderlo per eseguire da 16k a 64k.

Puoi vedere il numero di connessioni aperte usando netstat -an. I socket potrebbero essere bloccati nello stato TIME_WAIT se si stanno aprendo e chiudendo molte connessioni. In alcuni casi questo è inevitabile, ma potrebbe essere necessario considerare se è necessario un pool di connessione in questo caso.

Se TIME_WAIT è il problema, è possibile impostare net.ipv4.tcp_tw_reuse/ net.ipv4.tcp_tw_recycleper accelerare il turnover della connessione.


+1, grazie per aver dedicato del tempo a fornire a questo ragazzo dettagli esatti.
Caleb,

Abbiamo un intervallo compreso tra 32800 e 61000. Scopriamo semplicemente che, una volta utilizzati, il sistema operativo non li utilizzerà più. Questo è un comportamento previsto, ma mi aspetterei che il sistema operativo si riavvii all'inizio una volta raggiunta l'ultima porta disponibile. Questo non sembra accadere però. Inoltre, solo per notare, questo non è un evento estremamente regolare. È intermittente ma abbiamo un gran numero di server.
JMc,


1
Per essere conforme a RFC 6335 /proc/sys/net/ipv4/ip_local_port_range deve essere un sottoinsieme di 49152-65535. Quindi ridurre l'estremità inferiore dell'intervallo a qualcosa di meno di 49152 comporta un certo rischio.
Kasperd,

mai l'utente net.ipv4.tcp_tw_recycle né net.ipv4.tcp_tw_reuse tranne se sei disperato e sai esattamente cosa stai facendo. Stai esponendo il tuo servizio a potenziali problemi di estensioni.
Kiwy,

3

Tenere presente che questo limite si applica per tupla unica (IP di origine, IP peer, porta peer). Pertanto sarà necessario raggruppare l'output di netstat/ ssper ciascuna di queste tuple e verificare quanto è vicino ciascun gruppo al limite di connessione.

Questo post spiega come è possibile eseguire questo raggruppamento in modo più dettagliato. Per verificare la vicinanza di ciascun gruppo al limite in Ruby, è possibile elaborare un ssoutput come:

#!/usr/bin/ruby

first_port, last_port = IO.read('/proc/sys/net/ipv4/ip_local_port_range').split.map(&:to_i)
ephemeral_port_max = last_port - first_port + 1
ephemeral_port_warning = ephemeral_port_max / 3 * 2

conns = `ss --numeric --tcp state connected "( sport >= :#{first_port} and sport <= :#{last_port} )"`

groups = Hash.new(0)
conns.lines.each do |conn|
  state, recvq, sendq, local, peer = conn.split
  local_ip, local_port = local.split(':')
  group = [local_ip, peer]
  groups[group] += 1
end

groups_requiring_warning =
  groups.select { |k, v| v > ephemeral_port_warning }
  .to_a
  .sort_by { |v1, v2| v1[1] <=> v2[1] } # Sort groups in descending order of number of connections

groups_requiring_warning.each do |group, used_port_count|
  puts "Connections from #{group[0]} to #{group[1]} "\
    "have used #{used_port_count} ephemeral ports out of #{ephemeral_port_max} max"\
    "(#{((used_port_count.to_f / ephemeral_port_max) * 100).round(2)}% used)"
end
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.