PHWinfo banniere

Titres
PORTAIL ANNUAIRE ARTICLES COMPARATEUR HÉBERGEURS DEVIS FORUMS RÉDUCTEUR D'URL
Précédent   PHWinfo > Forums Hébergement > Forum Noms de domaine > comp.protocols.tcp-ip > select() woes
S'inscrire FAQ Membres Recherche Messages du jour Marquer les forums comme lus
comp.protocols.tcp-ip TCP and IP network protocols.

select() woes

Réponse
 
LinkBack Outils de la discussion
Vieux 17/10/2006, 20h47   #1
Generic Usenet Account
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut select() woes

I created a very UDP simple server (Linux kernel 2.4.20) that listens
on two ports --- 6000 & 7000. I am using select(), but I am seeing
some unexpected behavior. The server seems to get "locked" on to the
port number on which it receives its first message. For example, if
the first message to the server is sent on port 6000, it will receive
all subsequent messages on port 6000, but it will simply ignore all
messages on port 7000. Similarly, if the first message to the server
is sent on port 7000, it will receive all subsequent messages on port
7000, but it will turn deaf to port 6000.

I am sure that there is some careless mistake on my part. Any
will be appreciated.

Regards,
Song

///// Sample Source Code /////
#include <unistd.h>
#include <ctype.h>
#include <iostream>
#include <time.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <netinet/in.h>
#include <arpa/inet.h>

using namespace std;

#define MAXMESG 2048

#define PORT_1 6000
#define PORT_2 7000


int maxDescriptor_g = 0;

//////////////////////////////////////////////////////////
//
// Simply dumps the message contents in hex
//
//////////////////////////////////////////////////////////
void
printMessage(void *msg, size_t msgLen)
{
ios_base::fmtflags oldFmtSettings = cout.setf(ios::showbase);
char *msgPtr = (char *)msg;
for(size_t i = 0; i < msgLen; i++)
{
if(!(i%10))
cout << endl;
unsigned char ch = *(msgPtr+i);
cout << hex << int(ch) << " ";
}
cout << endl;
cout.setf(oldFmtSettings);

cout <<"\n\n\n";
}


//////////////////////////////////////////////////////////
//
// Processes incoming message
//
//////////////////////////////////////////////////////////
void
processMsg(int sockd)
{
int bytesRead, clilen;

char mesg[MAXMESG];
sockaddr_in from;

size_t addrLen = sizeof(sockaddr_in);
size_t msgLen;


for(;
{
bytesRead = recvfrom(sockd, mesg, MAXMESG, 0,(sockaddr*) &from,
(socklen_t *)&addrLen);
if(bytesRead < 0)
{
cerr << "recvfrom: error" << endl;
continue;
}

cout << "Received following message from " <<
inet_ntoa(from.sin_addr)
<< ":\n";
printMessage(mesg, bytesRead);
break;
}
}


//////////////////////////////////////////////////////////
//
// Makes calls to socket(), bind() etc.
//
//////////////////////////////////////////////////////////
int
registerNewListener(int& sd, unsigned short portNum, fd_set& readSet)
{
sockaddr_in serverDetails;
serverDetails.sin_family = AF_INET;
serverDetails.sin_addr.s_addr = htonl(INADDR_ANY);
serverDetails.sin_port = htons(portNum);

socklen_t serverAddrLen = sizeof(sockaddr_in);

if((sd=socket(AF_INET, SOCK_DGRAM, 0)) < 0)
{
cerr << "server: can't open datagram socket" << endl;
return -1;
}

if(bind(sd, (const sockaddr*)&serverDetails, serverAddrLen) < 0)
{
cerr << "server: can't bind local address" << endl;
close(sd);
return -2;
}

int on = 1;
if(ioctl(sd, FIONBIO, &on) < 0)
{
cerr << "server: can't set the socket to non-blocking" << endl;
return -3;
}

FD_SET(sd, &readSet);

if(sd > maxDescriptor_g)
maxDescriptor_g = sd;

return 0;
}


//////////////////////////////////////////////////////////
//
// main
//
//////////////////////////////////////////////////////////
main(int argc, char *argv[])
{
int sockd1, sockd2;

fd_set readFDSet;
FD_ZERO (&readFDSet);

if(registerNewListener(sockd1, PORT_1, readFDSet) < 0)
{
return -1;
}


if(registerNewListener(sockd2, PORT_2, readFDSet) < 0)
{
return -1;
}

for(;
{
int rc;
if((rc = select(maxDescriptor_g+1, &readFDSet, NULL, NULL, NULL)) <
1)
{
cerr << "server: Bad return value from select (" << rc << ")\n";
return -3;
}

if(FD_ISSET(sockd1, &readFDSet))
processMsg(sockd1);

if(FD_ISSET(sockd2, &readFDSet))
processMsg(sockd2);
}
}

  Réponse avec citation
Vieux 17/10/2006, 23h50   #2
Bob Hauck
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: select() woes

["Followup-To:" header set to comp.os.linux.misc.]

On 17 Oct 2006 12:47:32 -0700, Generic Usenet Account
<usenet@sta.samsung.com> wrote:

> I created a very UDP simple server (Linux kernel 2.4.20) that listens
> on two ports --- 6000 & 7000. I am using select(), but I am seeing
> some unexpected behavior. The server seems to get "locked" on to the
> port number on which it receives its first message.


[snip code]

> main(int argc, char *argv[])
> {
> int sockd1, sockd2;
>
> fd_set readFDSet;
> FD_ZERO (&readFDSet);
>
> if(registerNewListener(sockd1, PORT_1, readFDSet) < 0)
> {
> return -1;
> }
>
>
> if(registerNewListener(sockd2, PORT_2, readFDSet) < 0)
> {
> return -1;
> }
>
> for(;
> {
> int rc;
> if((rc = select(maxDescriptor_g+1, &readFDSet, NULL, NULL, NULL)) <
> 1)
> {
> cerr << "server: Bad return value from select (" << rc << ")\n";
> return -3;
> }
>
> if(FD_ISSET(sockd1, &readFDSet))
> processMsg(sockd1);
>
> if(FD_ISSET(sockd2, &readFDSet))
> processMsg(sockd2);
> }
> }


You only ever configure readFDSet in registerNewListener(). If you were
to read the man page for select() you would see this:

On exit, the sets are modified in place to indicate which file
descriptors actually changed status.

This means that you need to call FD_SET() again before each call to
select(). If you don't do that, then the set will only contain the
descriptors that changed, thus explaining the behavior you are seeing.


--
-| Bob Hauck
-| Have you had enough of George Bush yet?
-| http://www.haucks.org/
  Réponse avec citation
Réponse


Outils de la discussion

Règles de messages
Vous ne pouvez pas créer de nouvelles discussions
Vous ne pouvez pas envoyer des réponses
Vous ne pouvez pas envoyer des pièces jointes
Vous ne pouvez pas modifier vos messages

Les balises BB sont activées : oui
Les smileys sont activés : oui
La balise [IMG] est activée : oui
Le code HTML peut être employé : non
Trackbacks are oui
Pingbacks are oui
Refbacks are oui


Fuseau horaire GMT +1. Il est actuellement 17h12.


Édité par : vBulletin® version 3.7.3
Copyright ©2000 - 2008, Jelsoft Enterprises Ltd.
Search Engine Friendly URLs by vBSEO 3.2.0 RC5 Tous droits réservés.
Version française #16 par l'association vBulletin francophone
PHWinfo est un site Éducation Sans Frontières ©2000-2008
Ad Management by RedTyger
©Tous droits réservés par les parties respectives
Page generated in 0,11448 seconds with 10 queries