Как убедиться, что send() доставил данные получателю при работе в неблокирующем режиме?
Вызываю send() — возвращает ОК(все отправлено). выдергиваю сетевой шнур, снова send() — ОК и только через некоторое время TCP сообщает, что коннект разорван. Но как узнать, что дошло до получателя, а что нет (какие send были ДЕЙСТВИТЕЛЬНО успешны)?
Заранее благодарю.
Здравствуйте, Аноним, Вы писали:
А>Как убедиться, что send() доставил данные получателю при работе в неблокирующем режиме? А>Вызываю send() — возвращает ОК(все отправлено). выдергиваю сетевой шнур, снова send() — ОК и только через некоторое время TCP сообщает, что коннект разорван. Но как узнать, что дошло до получателя, а что нет (какие send были ДЕЙСТВИТЕЛЬНО успешны)? А>Заранее благодарю.
гарантированно — только с использованием подтверждающего пакета от получателя
Re[2]: send() и неблокирующий режим
От:
Аноним
Дата:
15.05.03 06:11
Оценка:
т.е. самому ручками реализовывать? Тогда уж проще UDP использовать.
Неужели при работе в неблокирующем режиме гарантированность доставки сообщений по TCP — понятие довольно относительное?
Здравствуйте, Аноним, Вы писали:
А>т.е. самому ручками реализовывать? Тогда уж проще UDP использовать. А>Неужели при работе в неблокирующем режиме гарантированность доставки сообщений по TCP — понятие довольно относительное?
в любом, и блокирующем и не блокирующем.... да, немного относительное понятие
если интересует момент окочания отправки то в неблокирующем message-based сокете придет событие FD_WRITE
или аналогичное событие при WSAEventSelect и т.п.
Здравствуйте, Аноним, Вы писали:
А>Как убедиться, что send() доставил данные получателю при работе в неблокирующем режиме? А>Вызываю send() — возвращает ОК(все отправлено). выдергиваю сетевой шнур, снова send() — ОК и только через некоторое время TCP сообщает, что коннект разорван. Но как узнать, что дошло до получателя, а что нет (какие send были ДЕЙСТВИТЕЛЬНО успешны)? А>Заранее благодарю.
Все дело в буферизации. Так в windows 2000 можно отправить до 1 MB данных и Send вернет OK даже если клиент еще и не начал получать. Это сделано для ускрония работы стека в целом ( более подробно следует прочитать про механизм медленного старта и т.п. ). Таким образом без ответа от клиента действительно нельзя быть увереным что данные получены. TCP лишь гарантирует целостность пакетов и то что они придут в правильном порядке. Реализововать на UDP самому это не так то просто.
Re[2]: send() и неблокирующий режим
От:
Аноним
Дата:
15.05.03 06:49
Оценка:
Чтож, все понятно. Придется самому гонять подтверждение на каждое сообщение.
Спасибо за комментарии.
Кстати, каким параметром задать время реакции на "живучесть коннекта", чтоб TCP быстрее соображал, что коннект умер?
Здравствуйте, Аноним, Вы писали:
А>Чтож, все понятно. Придется самому гонять подтверждение на каждое сообщение. А>Спасибо за комментарии. А>Кстати, каким параметром задать время реакции на "живучесть коннекта", чтоб TCP быстрее соображал, что коннект умер?
а вот так и сделать... если ответ на посылку не пришел за N секунд — то умер....
для этих целей специально делают пульс-сообщения (типа пинг-понг)
почитай Йона Шнейдера "Эффективное программирование TCP/IP"
Re[4]: send() и неблокирующий режим
От:
Аноним
Дата:
15.05.03 07:25
Оценка:
Здравствуйте, NeuroVirus, Вы писали:
NV>а вот так и сделать... если ответ на посылку не пришел за N секунд — то умер.... NV>для этих целей специально делают пульс-сообщения (типа пинг-понг) NV>почитай Йона Шнейдера "Эффективное программирование TCP/IP"
Это все понятно. Я имел ввиду стандартное поведение TCP сокета. Можно ли программно задать время, через которое придет FD_READ и recv() вернет SOCKET_ERROR? Или это зависит от конкретной реализации?
Здравствуйте, Аноним, Вы писали:
А>Здравствуйте, NeuroVirus, Вы писали:
NV>а вот так и сделать... если ответ на посылку не пришел за N секунд — то умер.... NV>для этих целей специально делают пульс-сообщения (типа пинг-понг) NV>почитай Йона Шнейдера "Эффективное программирование TCP/IP"
А>Это все понятно. Я имел ввиду стандартное поведение TCP сокета. Можно ли программно задать время, через которое придет FD_READ и recv() вернет SOCKET_ERROR? Или это зависит от конкретной реализации?
я сам не искал, а Шнейдер говорит что можно (и то непросто) но только для всех соединений сразу (т.е. это параметр TCP/IP стека в целом)
Re[6]: send() и неблокирующий режим
От:
Аноним
Дата:
15.05.03 07:51
Оценка:
Здравствуйте, NeuroVirus, Вы писали:
NV>я сам не искал, а Шнейдер говорит что можно (и то непросто) но только для всех соединений сразу (т.е. это параметр TCP/IP стека в целом)
ОК. Шнейдера скачал — погляжу вечерком. Еще раз спасибо за полезную инфу.
Здравствуйте, Guardian76, Вы писали:
G>Все дело в буферизации. Так в windows 2000 можно отправить до 1 MB данных и Send вернет OK даже если клиент еще и не начал получать. Это сделано для ускрония работы стека в целом ( более подробно следует прочитать про механизм медленного старта и т.п. ). Таким образом без ответа от клиента действительно нельзя быть увереным что данные получены. TCP лишь гарантирует целостность пакетов и то что они придут в правильном порядке. Реализововать на UDP самому это не так то просто.
Прошу прощения за вмешательство, но тоже волнует эта проблема...
А если соединение пропадет в момент посылки подтверждающего ответа? Что тогда? Посылать ответ на подтверждение получения подтверждающего ответа?
Здравствуйте, ringtail, Вы писали:
R>Прошу прощения за вмешательство, но тоже волнует эта проблема... R>А если соединение пропадет в момент посылки подтверждающего ответа? Что тогда? Посылать ответ на подтверждение получения подтверждающего ответа?
R>С уважением
Я так понимаю, что это вопрос стратегический, т.е. кто заинтересован в гарантиях.
например есть сервер и клиент, клиент делает запрос, получает ответ.
В нашем случае запросом будет передача сообщения а ответом является квитанция об
успехе (или неуспехе) доставки сообщения.
Как и вреальной жизни при получении сообщения мы ждем какое-то время, а потом
можем сделать 2 вещи: 1) да пропади оно все, мне уже наплевать.... или
2) эй, милейший, еще раз спрашиваю, так как там оно?
Таким образом надо определить: величину таймаута, кол-во запросов на повтор
подтверждения и стратегию поведения при отсутствии ответов (увеличение
таймаута до след. запроса, разрывы соединений, откаты и т.п.)
Если сервер заинтересован в том, чтобы иметь гарантию доставки своего подтверждения,
то в данном случае клиент и сервер меняются местами (да, клиент будет высылать
подтверждение, что получил квитанцию) — сервер будет спрашивать клиента при
отсутствии квитанции2 в разумное время.
Ничего страшного тут нет, ежели уж нужна ГАРАНТИЯ то будте любезны обеспечить.