Reputation: 146
Scenario: when select detect activity in one socket then below criteria happens in my code.
pseudo code:
after select i am checking in
if stdin f descriptor
do something
else if listening file descriptor
newFDescriptor = accept sockFDescriptor, (struct sockaddr *) &clientAddress, &clientAddressSize
FD_SET (new file descriptor)
send connected response to peer
// data from connected peer
else {
receive data
}
But every time i send something from a peer to other it creates new connection with new filedescriptor. i.e. it doesn't recogonize data in already created filedescriptor for this peer. peer 1 to peer 2 (new file descriptor created) peer 1 to peer 2 (again new connection) It is receiving all data on the listening file descriptor.
Upvotes: 1
Views: 940
Reputation: 310840
If the peer insists on creating a new connection there's nothing you can do about it at the server end.
"It is receiving all data on the listening file descriptor" doesn't begin to make sense. It's impossible. The listening file descriptor can't do anything except accept connections.
Upvotes: 1
Reputation: 4666
I agree with jedwards (+1) -- you should read the Beej's Guide to get you started.
In the mean time, here is some quick input that might help in avoiding the error you are running into. My guess is that you are mixing up the file descriptors.
You would need to add the new file descriptors (the ones from the accept() call) into a list and then use them (also) to populate the fd set for the next select call. The listener fd is only for establishing new connections and subsequent accept() -- you should not be calling receive or send on that fd (let us call it server_fd).
Here is a quick example code that stores all connections in an array, then you can set the fd as follows. For indices of the array that do not have a valid fd, it uses -1.
FD_ZERO(&read_fd_set);
/* Set the fd_set before passing it to the select call */
for (i=0;i < MAX_CONNECTIONS;i++) {
if (all_connections[i] >= 0) {
FD_SET(all_connections[i], &read_fd_set);
}
}
ret_val = select(FD_SETSIZE, &read_fd_set, NULL, NULL, NULL);
Once the select returns, you can check if the fd with the read-event is the server fd and if so, you can call accept() to get the new fd -- you need to add it to the array. Something like this:
if (FD_ISSET(server_fd, &read_fd_set)) {
new_fd = accept(server_fd, (struct sockaddr*)&new_addr, &addrlen);
if (new_fd >= 0) {
printf("Accepted a new connection with fd: %d\n", new_fd);
for (i=0;i < MAX_CONNECTIONS;i++) {
if (all_connections[i] < 0) {
all_connections[i] = new_fd;
break;
}
}
}
}
Upvotes: 0