о вызове Select

  • Автор темы debug
  • Дата начала
Статус
Закрыто для дальнейших ответов.
D

debug

#1
Сначала опишу в кратце - решил я воспользоваться вызовом select при общении с TCP сервером. Сервер не моей разработки - пакетики шлёт странно как то - небольшими порциями - иногда байт по 20. Но так получилось - что без него нни куда %(
причина ясна - хотя сокет планирую открывать с ним пока один - но решил через select пообщаться. Примерно код такой
сначала создание сокета PF_INET, как обычно, затем connect - конектится всё в порядке, затем:

for (;:( {
fd_set rfdset, wfdset;
FD_ZERO(&rfdset);
FD_ZERO(&wfdset);
if (!readden) {
FD_SET(sock, &rfdset);
cout<<"readden=false\n";
}
if (!written) {
FD_SET(sock, &wfdset);
cout<<"written=false\n";
}
memset(read_buf, 0, sizeof(read_buf));
int rc=select(sock+1, &rfdset, &wfdset, NULL, &tv);
if (!rc) {
closesocket(sock);
exit_error("timeout", WSAGetLastError());
}
if (rc<0) {
closesocket(sock);
exit_error("error select - WSAGetLastError: ") }
if (FD_ISSET(sock, &rfdset)) {
out(" есть данные для чтения");
int count_byte=recv(sock, read_buf, sizeof(read_buf), 0);
out("получены данные - байт:");
out(read_buf);
// if (count_byte==30) {
// readden=true;
// written=false;
}
}
if (FD_ISSET(sock, &wfdset)) {
out("возможна запись данных");
int sent_byte=send(sock, write_buf, strlen(write_buf), 0);
out("записано в порт байт: ");
out(sent_byte);
// if (sent_byte==strlen(write_buf)) {
// written=true;
// readden=false;
}
}
}
Суть вопросов:
1. Какие нужно опции ставить на сокет (setsockopt) перед использованием в select?
2. В каком режиме нужно "отдавать" select-у сокет - блокируемом или наоборот, тоже опционально setsockopt?
3. В моём примере с учётом комментариев всё работает - но вот какая штука,
я написал быстренько сервер - который сначала порцию байт принимает - затем отправляет клиенту небольшую порцию байт. Так вот весь прикол в следующем:
если timeval tv установлен больше 1 секунды - то происходит вот что - клиент сначала в сокет серверу одни и теже данные - много раз (хотя сервер принимает один пакет и сразу отправляет ответ), затем много раз читает из сокета пришедший от сервера пакет. Если tv установить в 0 - то клиент вообще ничего не успевает прочитать.
Я думал - что select работает таким образом - что однажды отправленные данные уже не отправит и не будет из буфера читать одно и тоже много раз. Выходит я сам должен управлять набором сокетов, переключая его в селекте в режим чтения или записи дабы избежать записи или чтения уже принятых или отправленных многократно данных???
Если есть конкретный у кого пример - напишите пожалуста
 
Статус
Закрыто для дальнейших ответов.