Jump to content
  • Advertisement
Sign in to follow this  
Retor

Noobish non-blocking question

This topic is 4427 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Okay, well I'm currently trying to get my small client up and running... but I have problems due to my poor knowledge with winsock. I'm trying to figure out which would be easiest to port over to other OS's in later releases, and I figured I should try blocking sockets, but treating them non-blockingly (i.e. with select() and minimal timeval). So, with the knowledge I've learned from a couple tutorials I tried doing this:
      switch(select(1, &socket_check, NULL, NULL, &_time))
      {
         case FD_READ:
            break;

         case FD_WRITE:
            break;

         case FD_CLOSE:
            break;
      }

Well, that obviously didn't work out. I was confused why, and realized I was supposed to be using asynchronous, which of course is only available on Win32 projects. Well, wanting to port this over later, that's not a very likely option for me. So my question goes out to you, what would be the best way to make this easy to port over later? Should I stick with select (if so, how do I use it properly?), or should I just make my sockets completely non-blocking, and if so how should I handle them? I'm terribly sorry for these noobish questions, but I'm utterly confused here. Basically all I need here is a little guidance, and if possible (I'd really appreciate it), where I should head to learn (yes, I want to do the work) about the option you recommend. I already read in the FAQ that for porting to Linux, me making non-blocking sockets combined with select would be best, but also what about Mac OSX? Either way, I appreciate you taking the time to read this. :)

Share this post


Link to post
Share on other sites
Advertisement
If you want highly portable socket code you should use the ACE toolkit.
The socket classes are pretty easy to get started with, though the more advanced concepts can be difficult to understand at first. There are a few books on it though.

Share this post


Link to post
Share on other sites
ACE is engineered for enterprise software like object brokers, not generally for games. It is also too large and heavy-weight for many game applications. I cannot recommend it (and thus, it's not part of the fine list of libraries found in the Forum FAQ).

The problem you're having is that you're confusing the output of select(). select() returs the number of sockets that are ready. You then go through the fd_sets you pass in, to see which sockets are actually ready, and service them as necessary.

Share this post


Link to post
Share on other sites
First, I suggest using non-blocking sockets. Don't do blocking with time intervals, that will just confuse you later. There's no reason not to just use non-blocking sockets.

Secondly, if you're programming for Windows, make sure that before you use select() that you set the socket to non-blocking. The syntax for this is different for Windows than other OS's: You'll want to use ioctlsocket() function (look it up).

Thirdly, you're using select() wrong.

Here's how to do it for clients (look for a better explanation here):

First, make the socket non-blocking. Then, call connect(). Since it's non-blocking, you might not immediately connect, but the program won't stall. It should return SOCKET_ERROR, but WSAGetLastError() will return WSAEWOULDBLOCK, which is what you expect, so all is good.

Later, when you want to see if you've connected yet, add your socket into an fd_set, using the FD_SET macro (this is explained in the link above), and call select(), with this fd_set being the third parameter (you are interested in seeing if this socket can write - if it can, it is because it is connected). Then check the fd_set with the FD_ISSET macro. If the socket is still in the set, then you are connected.

From then on, just call select() with an fd_set containing your socket in the 2nd parameter (since you are interested in reading) when you want to see if you've gotten any data and can call recv(). And you can send() normally.

Check out the link, avoid asynchronous sockets, and good luck (I tried async sockets - its harder, more complicated, and a headache that's not worth it).

-Gauvir_Mucca

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!