Jump to content

    
Ruslan1

Можно ли уменьшить количество TCP соединений со статусом "TIME_WAIT" на удаленном сервере?

Recommended Posts

30 minutes ago, Rst7 said:

Не надо заменять FIN на RST. Надо послать дополнительный сегмент (RST) при приходе валидного ACK в состоянии CLOSING и LAST-ACK.

Ну WireShark много чего красным красит. Это ж не повод для беспокойства в конкретно данном случае.

Понял, Спасибо.

Попробую. В любом случае сделаю опционально, чтоб через конфиг можно было включить передачу RST, а по дефолту чтоб без него.

Share this post


Link to post
Share on other sites
41 minutes ago, jcxz said:

Это делается для того, чтобы опоздавшие пакеты не были восприняты как часть нового соединения

Это понятно. Но есть нюанс. Связанный с ISS, который довольно бодро убежит вперед и опоздавшие пакеты будут отброшены следующим соединением (если вдруг чудо случится, и совпадут ip/port) как не попадающие в окно.

В общем, вероятность последующего провала из-за отказа от TIME_WAIT крайне невелика. Ну и давайте посмотрим правде в глаза, и скажем, что MSL в 120 секунд в наше время - это с явно излишним запасом.

Share this post


Link to post
Share on other sites
9 минут назад, Rst7 сказал:

Это понятно. Но есть нюанс. Связанный с ISS

Это что такое? Уж не про номера TCP-последовательностей ли, необнулямые при новом коннекте?

9 минут назад, Rst7 сказал:

Ну и давайте посмотрим правде в глаза, и скажем, что MSL в 120 секунд в наше время - это с явно излишним запасом.

Значение MSL можно принять соответствующим современным реалиям скорости доставки :wink2:

Share this post


Link to post
Share on other sites
29 minutes ago, jcxz said:

Не важно посылать или нет RST (или что-то другие внутри текущего соединения), от этого необходимость TIME_WAIT не исчезает.

Ну, я не хочу TCP переписать, я хочу его чуть допилить. ненормальные ситуации требуют необычных решений :).

 

Для меня важно, что ситуация остается в "правовом TCP поле" и я не изобретаю велосипед. В RFC это описано,  если принял RST (в указанных состояниях)- то закрывает и удаляет:

Quote

CLOSING STATE, LAST-ACK STATE

TIME-WAIT

If the RST bit is set then, enter the CLOSED state, delete the TCB, and return.

В-общем, похоже на мою хотелку: могу удалить соединение на сервере командой, посланной от клиента.

Share this post


Link to post
Share on other sites
2 hours ago, Ruslan1 said:

У меня кучка приборов рандомно данные кидают. И в результате кто-то часто достукивается, а кто-то раз в час получает "счастливый билетик". Ну, раз нельза вылечить, попробую просто упорядочить это безобразие.

Перечитал еще раз внимательнее всю тему.

Скорее всего у вас так называемые проблемы множественного доступа к среде передачи.

По простому , куча приборов стучит на один сервер.

Мне кажется что нужно упорядочить этот случайный конект к серверу.  Если прибор достучался до сервера - то следующий раз он обратится к серверу через  N*MSL . Если был отказ в доступе к серверу - то следующее время будет  (N-1)*MSL . Таким образом все приборы получат доступ к серверу.

Share this post


Link to post
Share on other sites
5 minutes ago, jcxz said:

Это что такое? Уж не про номера TCP-последовательностей ли, необнулямые при новом коннекте?

Именно.

5 minutes ago, jcxz said:

Значение MSL можно принять соответствующим современным реалиям скорости доставки 

Можно. Но, к сожалению, эта настройка на сервере крутится, а не на клиенте.

С другой стороны, клиент может послать RST не сразу по получению ACK на FIN, а через паузу. Ну, скажем, через 5 секунд. Именно этим сымитировав уменьшение настройки MSL на сервере.

Share this post


Link to post
Share on other sites
1 час назад, Rst7 сказал:

Именно.

А TCP-сервера по умолчанию не обнуляют их при новом коннекте? Если нет, то всё равно нужно допиливать исходный код TCP-стека сервера.

TCP-сервер не просто должен "не обнулять", а хранить эти номера последовательностей для каждого клиента, обнаруживать что происходит коннект с тем же самым клиентом (с кем уже был недавно коннект) и восстанавливать его номера TCP-последовательностей из истории.

А если уж есть доступ к исходному коду сервера, то проще увеличить количество доступных соединений. И необязательно делать соединения находящиеся в TIME_WAIT полнофункциональными: например up to 100 полнофункциональных соединений и up to 1000 - находящихся в TIME_WAIT (чтоб уменьшить требуемые ресурсы).

1 час назад, Ruslan1 сказал:

Ну, я не хочу TCP переписать, я хочу его чуть допилить. ненормальные ситуации требуют необычных решений :).

Если ваш сервер при каждом новом коннекте сбрасывает номера TCP-последовательностей (или ещё как-то их модифицирует), а не использует сохранённые номера от прошлого коннекта с тем же самым клиентом, то без переписывания кода сервера - никак. RST тут не поможет.

 

1 час назад, Ruslan1 сказал:

В-общем, похоже на мою хотелку: могу удалить соединение на сервере командой, посланной от клиента.

Мне кажется Вы не понимаете в чём проблема. Хотя уже не раз тут было о ней сказано.... :unknw:

Ну удалили Вы там что-то на сервере. Открыли быстро новое соединение (пока 2*MSL не истекло). Начали по нему обмениваться. И тут пришёл кадр, относящийся к старому соединению (с тем же самым клиентом с тем же самым TCP-портом на нём). И как прикажете TCP-стеку определять - этот кадр от старого соединения или от нового? Получите сбой в работе TCP-стека.

И никакие очистки или удаления чего-бы там ни было на TCP-сервере тут не помогут.

Наоборот - чтобы победить это, нужно хранить или номера TCP-последовательностей (на сервере) или локальный TCP-порт (на клиенте), а не удалять что-то.

Share this post


Link to post
Share on other sites
22 minutes ago, jcxz said:

А TCP-сервера по умолчанию не обнуляют их при новом коннекте?

Нет. Это сквозной счетчик, один на всех. Типа +1 каждые 0.1мкс, так рекомендовано (если мне память не изменяет). Тоже защита от старых пакетов.

 

Share this post


Link to post
Share on other sites
36 minutes ago, jcxz said:

Мне кажется Вы не понимаете в чём проблема. Хотя уже не раз тут было о ней сказано.... :unknw:

Ну удалили Вы там что-то на сервере. Открыли быстро новое соединение (пока 2*MSL не истекло). Начали по нему обмениваться. И тут пришёл кадр, относящийся к старому соединению (с тем же самым клиентом с тем же самым TCP-портом на нём). И как прикажете TCP-стеку определять - этот кадр от старого соединения или от нового? Получите сбой в работе TCP-стека.

И никакие очистки или удаления чего-бы там ни было на TCP-сервере тут не помогут.

Наоборот - чтобы победить это, нужно хранить или номера TCP-последовательностей (на сервере) или локальный TCP-порт (на клиенте), а не удалять что-то.

Я не понимаю, почему посылка (и прием) RST в документации TCP стека является штатным действием с предсказуемой реакцией, и не приводит к апокалипсису, а у Вас описан именно конец света. Хотя, может, я просто неправильно понял, что Вы понимаете под состоянием "сбой в работе TCP-стека".

Share this post


Link to post
Share on other sites
1 час назад, Rst7 сказал:

Нет. Это сквозной счетчик, один на всех. Типа +1 каждые 0.1мкс, так рекомендовано (если мне память не изменяет). Тоже защита от старых пакетов.

Видимо Вы имели в виду что-то другое... Под TCP-последовательностями я имел в виду: "Sequence Number" и "Acknowledgment Number" (RFC793 заголовок TCP). Они никак не зависят от времени, только от количества данных.

А что за счётчик Вы имели в виду? И как он участвует в процессе передачи внутри TCP-соединения?

57 минут назад, Ruslan1 сказал:

Хотя, может, я просто неправильно понял, что Вы понимаете под состоянием "сбой в работе TCP-стека".

Сбой произойдёт если например:

1) произошло соединение с клиентом1 (seqNr/ackNr = 0);

2) сервер отправил клиенту 10 байт данных (SEQ_10);  

3) клиент их не получил (данные застряли где-то по пути);

4) через N мсек сервер повторил отправку данных клиенту;

5) клиент получил их и ответил ACK_10;

6) они ещё пообменивались и закрыли соединение, или сразу закрыли (застрявшие данные ещё в пути);

7) не выдержав 2*MSL клиент1 вновь открыл соединение с сервером на тот же порт сервера с того же исходящего своего локального порта (номера последовательностей seqNr/ackNr = 0);

8) ....и тут клиенту приходит застрявший пакет!!! (так как 2*MSL с момента его отправки ещё не прошло) :shok:  Вот это и есть сбой. В текущее соединение пришли данные, которые сервер не посылал.

Как именно здесь поможет RST??? Объясните?

 

Именно для борьбы с такими ситуациями и служит TIME_WAIT.

Share this post


Link to post
Share on other sites
20 minutes ago, jcxz said:

номера последовательностей seqNr/ackNr = 0

Вот только не 0, а помянутый выше ISN - Initial Sequence Number. Так что вероятность сбоя по предложенной схеме, мягко говоря, крайне невелика.

Share this post


Link to post
Share on other sites
31 минуту назад, aaarrr сказал:

Вот только не 0, а помянутый выше ISN - Initial Sequence Number. Так что вероятность сбоя по предложенной схеме, мягко говоря, крайне невелика.

В таком случае - да.

Share this post


Link to post
Share on other sites
4 hours ago, aaarrr said:

а помянутый выше ISN - Initial Sequence Number.

Да, конечно, правильно - ISN, а не ISS. Пардон. "Что-то с памятью моей стало" (с)

Share this post


Link to post
Share on other sites
11 hours ago, Ruslan1 said:

Откуда вопрос возник: есть встроенный FTP сервер, где количество возможных соединений небольшое, и там в ограничение очень легко превысить, если много мелких файлов передавать: насколько я понял, каждый порт остается висеть эти 2*MSL и считается занятым. И очень хотелось бы помочь решить эту проблему со стороны клиента (если возможно), может действительно у меня в lwIP чего-то покрутить можно, и серверу станет легче.

Не понял кто кому шлет, сколько и что тормозит.  
В Azure RTOS с NetX Duo на платформе с Cortex-M4 240 МГц  на встроенный FTP сервер на базе SD карты спокойно перекачивается 1000 файлов без заметных задержек. 
Но вот сама SD карта после 500 файлов уже начинает заметно тормозить. 
Клиент - Total Comander.
Может тормоза от вашей файловой системы исходят, а не от FTP сервера. 

Да, и еще надо уточнять в пассивном или активном режиме идет перекачка. От этого зависит на чьей стороне идет прослушка портов. 
Но скажем FTP Azure RTOS и в пассивном и в активном режиме работает с одинаковой скоростью. 

Share this post


Link to post
Share on other sites

Мда. Много эротики и прочих непотребств на дороге этой вижу я. Ходить этим путем буду я совсем нет. А то снег башка попадет замучаюсь отчитываться перед контролирующими органами.

Всем спасибо. Уже понял, что путь с вставкой RST не такой безоблачный, как хотелось бы. Попробую другие варианты, а этот оставлю на совсем черный день.

 

А еще в течении часа копания в сорцах lwIP  кавалерийским наскоком не удалось мне всунуть дополнительный RST после последнего ACK, принятого сервером, чтоб это именно для конкретных соединений добавлялось, работало а не для всех. Там, скорее всего, еще один флаг в структуру TCB вводить.

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.