The OpenNET Project / Index page

[ новости /+++ | форум | теги | ]



Индекс форумов
Составление сообщения

Исходное сообщение
"отправка данных, сокеты"
Отправлено Alexander S. Salieff, 27-Июн-05 18:45 
>Как работает функция send для отправки данных? Какого время ее выполения? Какой
>интервал брать между последовательными вызовами? Заранее спасибо..

При "наобумном" вызове send'а на блокированном (а он такой по умолчанию) сокете выполнение программы блокируется на неопределенное время, пока не удастся отправить часть данных (совсем не обязательно будут отправлены все предложенные данные, возможно их придется отправлять частями).
Для гарантированной отправки данных с форматированием по временной сетке можно использовать 2 метода: неблокированный сокет с обработкой EAGAIN, либо демультиплексирование дескриптора на запись (poll/select). Я предпочитаю последнее, обертка для send'а с таймаутом выглядит у меня вот так:

int t_send(int s, const void *msg, size_t len, int flags, int timeout)
{
int my_timeout = timeout;
return t_send(s, msg, len, flags, &my_timeout);
}

int t_send(int s, const void *msg, size_t len, int flags, int * timeout)
{
if (*timeout<=0) return TNETWORK_ERR;
int curr_len=len;
int curr_timeout=*timeout;
while (curr_len>0 && curr_timeout>0)
  {
  timeb t1;
  ftime(&t1);
//Крутим poll в течении timeout
  struct pollfd ufds={s, POLLOUT, 0};
  int poll_ret = poll(&ufds, 1, curr_timeout);
  if (poll_ret<0)
   {
   if (errno==EINTR) //Прерывание сигналом
    {
    timeb t2;
    ftime(&t2);
    curr_timeout-=((t2.time-t1.time)*1000+t2.millitm-t1.millitm);
    continue;
    }
   else return TNETWORK_ERR;
   }
  if (poll_ret==0)
   return TNETWORK_TIMEOUT;
  if (!(ufds.revents&POLLOUT))
   return TNETWORK_ERR;
  int l=send(s, (unsigned char *)msg+(len-curr_len), curr_len, flags);
  if (l<0)
   {
   if (errno==EINTR)
    {
    timeb t2;
    ftime(&t2);
    curr_timeout-=((t2.time-t1.time)*1000+t2.millitm-t1.millitm);
    continue;
    }
   else return TNETWORK_ERR;
   }
  curr_len-=l;
  timeb t2;
  ftime(&t2);
  curr_timeout-=((t2.time-t1.time)*1000+t2.millitm-t1.millitm);
  }
*timeout-=curr_timeout;
return (len-curr_len);
}

Соответственно 1ый вариант просто с таймаутом, 2ой - с таймаутом и возвратом реально потраченного на операцию времени (часто бывает нужно для корекции именно той самой временной сетки)

 

Ваше сообщение
Имя*:
EMail:
Для отправки новых сообщений в текущей нити на email укажите знак ! перед адресом, например, !user@host.ru (!! - не показывать email).
Более тонкая настройка отправки ответов производится в профиле зарегистрированного участника форума.
Заголовок*:
Сообщение*:
 
При общении не допускается: неуважительное отношение к собеседнику, хамство, унизительное обращение, ненормативная лексика, переход на личности, агрессивное поведение, обесценивание собеседника, провоцирование флейма голословными и заведомо ложными заявлениями. Не отвечайте на сообщения, явно нарушающие правила - удаляются не только сами нарушения, но и все ответы на них. Лог модерирования.

На сайте действует частичное премодерирование - после публикации некоторые сообщения от анонимов могут автоматически скрываться ботом. После проверки модератором ошибочно скрытые сообщения раскрываются. Для ускорения раскрытия можно воспользоваться ссылкой "Сообщить модератору", указав в качестве причины обращения "скрыто по ошибке".



Партнёры:
PostgresPro
Inferno Solutions
Hosting by Hoster.ru
Хостинг:

Закладки на сайте
Проследить за страницей
Created 1996-2024 by Maxim Chirkov
Добавить, Поддержать, Вебмастеру