Últimamente, nos hemos dado cuenta de un problema de conexión TCP que se limita principalmente a los usuarios de Mac y Linux que navegan por nuestros sitios web.
Desde la perspectiva del usuario, se presenta como un tiempo de conexión muy largo con nuestros sitios web (> 11 segundos).
Hemos logrado rastrear la firma técnica de este problema, pero no podemos entender por qué está sucediendo o cómo solucionarlo.
Básicamente, lo que sucede es que la máquina del cliente está enviando el paquete SYN para establecer la conexión TCP y el servidor web lo recibe, pero no responde con el paquete SYN / ACK. Después de que el cliente ha enviado muchos paquetes SYN, el servidor finalmente responde con un paquete SYN / ACK y todo está bien para el resto de la conexión.
Y, por supuesto, la patada al problema: es intermitente y no ocurre todo el tiempo (aunque ocurre entre el 10 y el 30% del tiempo)
Estamos utilizando Fedora 12 Linux como sistema operativo y Nginx como servidor web.
Captura de pantalla del análisis de Wirehark
Actualizar:
Desactivar el escalado de la ventana en el cliente detuvo el problema. Ahora solo necesito una resolución del lado del servidor (no podemos hacer que todos los clientes hagan esto) :)
Actualización final:
La solución fue desactivar el escalado de ventanas TCP y las marcas de tiempo TCP en nuestros servidores que son accesibles al público.
fuente
Respuestas:
Tuvimos exactamente el mismo problema. Solo deshabilitar las marcas de tiempo TCP resolvió el problema.
Para que este cambio sea permanente, ingrese una entrada
/etc/sysctl.conf
.Tenga mucho cuidado al deshabilitar la opción Escala de ventana TCP. Esta opción es importante para proporcionar el máximo rendimiento a través de Internet. Alguien con una conexión de 10 megabit / seg tendrá una transferencia subóptima si el tiempo de ida y vuelta (básicamente igual que el ping) es superior a 55 ms.
Realmente notamos este problema cuando había múltiples dispositivos detrás del mismo NAT. Sospecho que el servidor podría haberse confundido al ver marcas de tiempo de dispositivos Android y máquinas OSX al mismo tiempo, ya que ponen valores completamente diferentes en los campos de marca de tiempo.
fuente
En mi caso, el siguiente comando solucionó el problema con la falta de respuestas SYN / ACK del servidor Linux:
Creo que es más correcto que deshabilitar las marcas de tiempo TCP, ya que las marcas de tiempo TCP son útiles para un alto rendimiento (PAWS, escalado de ventanas, etc.).
La documentación
tcp_tw_recycle
indica explícitamente que no se recomienda habilitarlo, ya que muchos enrutadores NAT conservan las marcas de tiempo y, por lo tanto, se activa PAWS, ya que las marcas de tiempo de la misma IP no son consistentes.fuente
net.ipv4.tcp_tw_recycle
es la verdadera razón. Gracias.Me pregunto, pero ¿por qué para el paquete SYN (marco # 539; el que fue aceptado), faltan los campos WS y TSV en la columna "Información"?
WS es TCP Window Scaling y TSV es Timestamp Value . Ambos se encuentran en el campo tcp.options y Wireshark aún debería mostrarlos si están presentes. ¿Tal vez la pila TCP / IP del cliente reenvió un paquete SYN diferente en el octavo intento y esa fue la razón por la que se reconoció de repente?
¿Podría proporcionarnos los valores internos del marco 539? ¿SYN / ACK siempre viene para un paquete SYN que no tiene WS habilitado?
fuente
Nos encontramos exactamente con el mismo problema (realmente nos llevó bastante tiempo fijarlo al servidor sin enviar sincronización).
"La solución fue desactivar el escalado de ventanas tcp y las marcas de tiempo tcp en nuestros servidores que son accesibles al público".
fuente
Para continuar con lo que ha dicho Ansis, he visto problemas como este cuando el cortafuegos no es compatible con TCP Windows Scaling. ¿Qué firewall de marca / modelo hay entre estos dos hosts?
fuente
La falta de SYN / ACK podría deberse a límites demasiado bajos de su protección SYNFLOOD en el firewall. Depende de cuántas conexiones crea el usuario del servidor. El uso de spdy reduciría el número de conexiones y podría ayudar en una situación en la que
net.ipv4.tcp_timestamps
apagar no ayuda.fuente
Este es el comportamiento de un socket TCP de escucha cuando su reserva está llena.
Ngnix permite que el argumento del backlog para escuchar se establezca en la configuración: http://wiki.nginx.org/HttpCoreModule#listen
escuchar 80 backlog = num
Intente configurar num a algo más grande que el predeterminado, como 1024.
No garantizo que una cola de escucha completa sea realmente su problema, pero esto es una buena primera cosa para verificar.
fuente
Acabo de descubrir que los clientes TCP de Linux cambian su paquete SYN después de 3 intentos y eliminan la opción Escala de ventana. Supongo que los desarrolladores del kernel pensaron que esta es una causa común de falla de conexión en Internet
Explica por qué estos clientes logran conectarse después de 11 segundos (el TCP SYN sin ventanas ocurre después de 9 segundos en mi breve prueba con la configuración predeterminada)
fuente
Tuve un problema similar, pero en mi caso fue la suma de verificación TCP la que se calculó incorrectamente. El cliente estaba detrás de un veth y ejecutando ethtool -K veth0 rx off tx off hizo el truco.
fuente