• Announcements

    • khawk

      Download the Game Design and Indie Game Marketing Freebook   07/19/17

      GameDev.net and CRC Press have teamed up to bring a free ebook of content curated from top titles published by CRC Press. The freebook, Practices of Game Design & Indie Game Marketing, includes chapters from The Art of Game Design: A Book of Lenses, A Practical Guide to Indie Game Marketing, and An Architectural Approach to Level Design. The GameDev.net FreeBook is relevant to game designers, developers, and those interested in learning more about the challenges in game development. We know game development can be a tough discipline and business, so we picked several chapters from CRC Press titles that we thought would be of interest to you, the GameDev.net audience, in your journey to design, develop, and market your next game. The free ebook is available through CRC Press by clicking here. The Curated Books The Art of Game Design: A Book of Lenses, Second Edition, by Jesse Schell Presents 100+ sets of questions, or different lenses, for viewing a game’s design, encompassing diverse fields such as psychology, architecture, music, film, software engineering, theme park design, mathematics, anthropology, and more. Written by one of the world's top game designers, this book describes the deepest and most fundamental principles of game design, demonstrating how tactics used in board, card, and athletic games also work in video games. It provides practical instruction on creating world-class games that will be played again and again. View it here. A Practical Guide to Indie Game Marketing, by Joel Dreskin Marketing is an essential but too frequently overlooked or minimized component of the release plan for indie games. A Practical Guide to Indie Game Marketing provides you with the tools needed to build visibility and sell your indie games. With special focus on those developers with small budgets and limited staff and resources, this book is packed with tangible recommendations and techniques that you can put to use immediately. As a seasoned professional of the indie game arena, author Joel Dreskin gives you insight into practical, real-world experiences of marketing numerous successful games and also provides stories of the failures. View it here. An Architectural Approach to Level Design This is one of the first books to integrate architectural and spatial design theory with the field of level design. The book presents architectural techniques and theories for level designers to use in their own work. It connects architecture and level design in different ways that address the practical elements of how designers construct space and the experiential elements of how and why humans interact with this space. Throughout the text, readers learn skills for spatial layout, evoking emotion through gamespaces, and creating better levels through architectural theory. View it here. Learn more and download the ebook by clicking here. Did you know? GameDev.net and CRC Press also recently teamed up to bring GDNet+ Members up to a 20% discount on all CRC Press books. Learn more about this and other benefits here.
Sign in to follow this  
Followers 0
Xanather

Opinions on my multiplay solution

12 posts in this topic

Ive developed a prototype for a game I am developing, I am just wondering on what more experienced network programmers think on my approach.

General:[list]
[*]2D game, not a shooter obviously.
[*]Using TCP - prefixing all messages with message lengths, all handled in the download algorithm.
[*]Enabled NO_DELAY
[/list]
Server:[list]
[*]Server has a fixed game loop of 60 ticks each second
[*]At the start of each loop the server downloads all available data from all clients and tries to process any full messages received (i.e. if message length has been reached, etc...). During this stage, if a message received is for example, "player X moving left", then the server checks if the received coordinates from where the player moved from is not using any sort of speed hack by comparing current position in server memory (etc.. etc.. handled all of this), then all other connected clients have their upload buffer added to with this new movement message.
[*]During the middle of a game loop (where the game tick is processed) all new messages to upload are placed into their respectful client upload buffers. (i.e. a NPC moved left/right).
[*]Just before the end of the game loop the server uploads all data in all uploads buffers of all connected clients.
[*]At the end of the game loop, all connections are checked to see if everyone is still connected correctly.
[*]There is only one thread which handles all of this
[/list]

Client:[list]
[*]Client has a fixed game loop of 60 ticks each second
[*]Also downloads everything at the start of the loop
[*]Also uploads everything just before the end of the loop
[*]Checks the server connection at the end of the game loop
[*]There is also only one thread which handles all of this.
[/list]
What do you think about this approach? Obviously read/write calls from the network stream cannot be blocking calls.
All replies appreciated, thanks :)
0

Share this post


Link to post
Share on other sites
Just know that 60 updates per second is a lot. Not sure if this is for the Internet, but with TCP you might see stuttering so you might want to lower that down to 10 to 20 in the future depending on your requirements.
1

Share this post


Link to post
Share on other sites


Yeah, it is used over the internet. I thought about the frequency, but since the game I am making is not a similar to what a "shooter" game may use I thought why not.

Data is only sent when data actually needs to be sent, all messages are considered "important" and there's no need to constantly send out packets like that of what UDP connection may do. Edited by Xanather
0

Share this post


Link to post
Share on other sites
My considerations:
- If you have some kind of id for each message, you mostly don't need to send the size of the message to the server (most of the messages will have an exact size).
- If you are using TCP, what do you mean by all connections are checked? I assume you are using select to implement this, since it is single-threaded, so the socket will be set and your receive will receive 0 bytes when a connection is finished or possibly a -1 if something went really wrong.
1

Share this post


Link to post
Share on other sites
@KnolanCross
That idea about specific id not needing certain message lengths is interesting, might implement that.
For your second point it is important to note that I am only downloading data if .IsDataAvailable returns true (using .net TcpClient class) so the thread doesn't block. Only at the end of the loop each connection is checked by checking .Connected. This field only returns false though after a failed read/write, and just before the connections are checked necessary data is Uploaded to all clients meaning any failed uploads will render the .Connected field false.

What do you think about that?
0

Share this post


Link to post
Share on other sites
Don't really know how the .net API works so I can't really tell if there is a better way to do so.

The points I would check are:
- Assuming .IsDataAvailable blocks the thread, will it return true if a connection drops?
- What happens is if the clients don't ask for updates when its idle (I am not assuming this happens, but with your explanation I couldn't be 100% sure) or if no client is connected. Wouldn't your simulation stop then?

Whenever you have a blocking single threaded approach is mostly good to have a timeout in the blocking part to check if everything is ok and avoid the program to stay locked forever. Other than that everything looks fine.

If it is a non-blocking API, I would recomend you to move to a blocking one, since a non-blocking approach is away more expensive. Edited by KnolanCross
2

Share this post


Link to post
Share on other sites
Sorry .IsDataAvailable is called NetworkStream.DataAvailable.

Anyway on MSDN it says:
[quote]Use the DataAvailable property to determine if data is ready to be read. If DataAvailable is true, a call to Read returns immediately. If the remote host shuts down or closes the connection, DataAvailable may throw a SocketException.[/quote]
So I thought checking DataAvailable would never throw a exception/block the thread unless the remote (client closes the connection) - but that wont happen anyway because Ive handled graceful disconnects.

For point 2: the client would eventually get disconnected from the server either way (say if a NPC moved nearby). On the client side a latency message is sent every 500ms so they would loose connection always if the servers drops.

Regarding having only one single thread: I just didn't want to create a new thread for each new client (255 clients mean 255 threads). Do you think it is safe to use the .net Task Parallel Libraries on the main thread if it is needed? I am also planning to move to .net 4.5 and make extensive use of the new .net Async methods soon. Ill just slap a async keyword on every method that has a chance to block.

Thanks for reply's btw, really helps [img]http://public.gamedev.net//public/style_emoticons/default/smile.png[/img] Edited by Xanather
0

Share this post


Link to post
Share on other sites
[quote]checking DataAvailable would never throw a exception/block the thread unless the remote (client closes the connection)[/quote]

That is correct.

[quote]didn't want to create a new thread for each new client[/quote]

That is also correct.

[quote]use of the new .net Async methods[/quote]

You can do many cool things with those!

[quote]just slap a async keyword on every method that has a chance to block[/quote]

That is not necessarily the right thing to do. Async development needs more careful design and planning than that.
1

Share this post


Link to post
Share on other sites
My point is that what it seems to me by your explanation is that your game loop depends on the receiving of messages or a disconect exception by the client. If none of those arrives, it will be in blocking state forever. You said that the client will send a message every 500 ms, but then you are assuming that the clients will play fair, this may lead to security issues.

Let me try to explain the problem this may cause with an example:
Assuming you will have multiple single threaded servers running multiple instances (each instance is a match where one or more players can play). I can create a hacked client that will:
1) Mimic the behavior of an original program until I get into a new world for myself. Up to here I am a normal client.
2) By the point I should start sending messages to the server, I just don't send anything.
3) The server is in a blocking state, waiting for info that will never arrive.

In this scenario the client will not be dropped because the hacked client can send TCP keepalive packages, which will keep the connection up. This is a "vandalism hacking attack" that your server may be susceptible.
You should set a server-side timeout on this so it will take actions every few ms even if no client sent any messages to avoid this kind of attack. As I said, I don't know anything about C# (I am a C/python programmer), but I believe the method you should look is this one:
[url="http://msdn.microsoft.com/en-us/library/bk6w7hs8%28v=vs.80%29.aspx"]http://msdn.microsof...8(v=vs.80).aspx[/url] (NetworkStream.ReadTimeout) Edited by KnolanCross
2

Share this post


Link to post
Share on other sites
Well, that does make sense, but the latency messages arn't necessarily "keepalive" message.

About a hacker trying to crash the server; all the establish-connection related stuff IS in a separate thread (should have probably said that xD), after the client/server handshake with a sequence of bytes then both the client/server go into "gameplay" mode, changing from the "login" mode (the server adds the client to the list of clients for the client to be iterated though on the main thread), the game state also changes on the client side and the client can now play. After that I don't think there are any game related messages that can actually freeze the server. The hacker could surely freeze the thread in the separate "establish-connection" thread, but that'd be pointless lol (but they could also create a infinite amount of pointless threads by doing this, I actually thought of this and will probably implement a timeout value so the hacked client just gets dropped, liked you said).

[quote name='hplus0603' timestamp='1353428357' post='5002694']
That is not necessarily the right thing to do. Async development needs more careful design and planning than that.
[/quote]
Haha yeah I know xD

Thanks,
Xanather. Edited by Xanather
0

Share this post


Link to post
Share on other sites
Not only that (creating loads of useless threads), sometimes you have small interpolated actions based on last time difference.
For instance, on a general approach, you have the movement calculated in something similar to (this example is a client server game I coded for college some time ago):

[source lang="python"] def calcNewPosition(self, movespeed, timeInterval, ang):
posTuple = self.getPos()
x = posTuple[0] + (movespeed * (timeInterval) * sin(radians(ang)))
y = posTuple[1] + (movespeed * (timeInterval) * cos(radians(ang)))
z = posTuple[2]

return (x, y, z)
[/source]
If the client can "freeze" the server, it may make the time inverval vary so much that it will end up "teleporting" in the game. If this happens, the collision calculation won't be effective and the character may end up being able to cross walls, fly or just create some unhandled situation that may end up with a crash. Edited by KnolanCross
0

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0