We run a number of services, which expose data on https listeners
Lately we have seen issues which might be related to problems with low-level TCP/IP packets
Could be a client is not responding timely with ACK to our network packets
Or filling up our TCP/IP stack by sending us requests and only receiving the response very slowly
Or maybe even lost network packets and retransmit
Is it possible to monitor and capture problems with TCP/IP messages in a C# service?
Related
Is there any common practice technique to send heartbeat message to monitor the client devices?
What I am doing currently is setup a tasktimer and polling each client device at one second interval and wait for client device's to acknowledge before incrementing the counter to poll the second device.
If there is no acknowledgement from a device, I will attempt again up to 3 tries.
Is this a good practice?
Please advise.
Thanks.
TCP provides reliable, ordered, and error-checked delivery of a stream of octets (bytes) between applications running on hosts communicating via an IP network. Applications that do not require reliable data stream service may use the User Datagram Protocol (UDP), which provides a connectionless datagram service that emphasizes reduced latency over reliability. Ref: "wiki".
In general, if your server and clients work in:
wired network instead of wireless network
neither of them crashes
No need to implement a heartbeat.
While heartbeat/PING/keep-alive is absolute or only working way to check the connection. But how to implement a heartbeat is a good practice or best for you, depends on your use case, for example, how often the heartbeat is efficient for you? The possible reasons for the client lost connection.
More refences:
"Do I need to heartbeat to keep a TCP connection open?"
"Keep Alive TCP/IP connected sockets over the Internet - when? how? and how much?"
"TCP Dead link detection"
I'm working on a game that depends on the standard System.Net.Sockets library for networking. What's the most efficient and standardized "system" I should use? Should the client send data requests every set amount of seconds, when a certain event happens? My other question, is a port forward required for a client to listen and receive data? How is this done, is there another socket created specifically for listening only on the client? How can I send messages and listen on the same socket on the client? I'm having a difficult time grasping the concept of networking, I started messing with it two days ago.
Should the client send data requests every set amount of seconds, when a certain event happens?
No. Send your message as soon as you can. The socket stack has algorithms that determine when data is actually sent. For instance the Nagle algorithm.
However, if you send a LOT of messages it can be beneficial to enqueue everything in the same socket method call. However, you need to send several thousand of messages per client and second for that to give you any benefit.
My other question, is a port forward required for a client to listen and receive data?
No. Once a socket connection have been established it's bidirectional. i.e. both end points and send and receive information without screwing something up for the other end point.
But to achieve that you typically have to use asynchronous operations so that you can keep receiving all the time.
How is this done, is there another socket created specifically for listening only on the client?
The server has a dedicated socket (a listener) which only purpose is to accept client sockets. When the listener have accepted a new connection from a remote end point you get a new socket object which represents the connection to the newly connected endpoint.
How can I send messages and listen on the same socket on the client?
The easiest way is to use asynchronous receives and blocking sends.
If you do not want to take care of everything by yourself, you can try my Apache licensed library http://sharpmessaging.net.
Creating a stable, high quality server will require you to have a wealth of knowledge on networking and managing your objects.
I highly recommend you start with something smaller before attempting to create your own server from scratch, or at the very least play around with a server for a different game that's already made, attempt to improve upon it or add new features.
That being said, there are a few ways you can setup the server, if you plan on having more than a couple of clients you don't generally want them to all send data whenever they feel like it as this can bog down the server, you want to structure it in such a way that the client sends as little data as possible on a scheduled basis and the server can request more when its ready. How that's setup and structured is up to you.
A server generally has to have a port forwarded on the router in order for requests to make it to the server from the internet, and here is why. When your computer makes a connection to a website (stackoverflow for example) it sends out a request on a random port, the router remembers the port that you sent out on and remembers who sent it (you), when the server sends the information you requested back the router knows you wanted that data and sends it back to you, in the case of RUNNING a server there is no outbound request to a client (Jack for example), so the router doesnt know where jacks request is supposed to go. By adding a port forwarding rule in the router your saying that all information passed to port 25565 (for example) is supposed to go to your server.
Clients generally do not need to forward ports because they are only making outbound requests and receiving data.
Server Starts, server starts listening on port 25565
Client starts, client connects to server on port 25565 and initiates a connection
Server responds to client on whatever port the client used to connect (this is done behind the scenes in sockets)
Communication continues from here.
I am writing a proxy for an application that uses RTSP for streaming video content. It basically works as follows:
The application (server) makes an RTSP stream available on localhost
port 8554.
A client wishing to connect to this stream connects to my
proxy on localhost port 8553.
My proxy connects to the RTSP stream (server) on localhost port 8554 and passes the network traffic (bytes) along between client and server. (I don't inspect packets at all, I simply read the bytes on the one stream and pass those bytes along to the other stream.)
Since RTSP uses both TCP and UDP communication, I will have to have listeners for both protocols on the proxy, however, I have not yet got to implementing the UDP part. At the moment I am simply working on TCP which essentially handles the "handshaking" to start the video transfer. The actual video transfer over UDP will be my next step.
Now for my question: I am successfully passing messages ("OPTIONS", "DESCRIBE", "SETUP, etc.) along with the proxy. The problem is that the content of the messages itself contains some information about the streaming server. Specifically, when the server responds to the client's "DESCRIBE" request, it returns amongst others:
Content-Base: rtsp://127.0.0.1:8554/nurv/
Before passing it along to the client, I need to change this on the proxy to:
Content-Base: rtsp://127.0.0.1:8553/nurv/
because at the moment, when the client issues the subsequent "SETUP" request, it requests:
SETUP rtsp://127.0.0.1:8554/nurv/track1 RTSP/1.0
which means that for the actual streaming it bypasses my proxy on port 8553 and connects directly to the stream on 8554.
How can I modify the messages on the proxy so that references to the actual server (i.e. 127.0.0.1:8554) get replaced by references to the proxy (i.e. 127.0.0.1:8553)? Obviously it isn't optimal to do a string search through each message being passed through the proxy since that would mean unpacking and inspecting each message before repacking and sending on.
I have solved this problem. Since the TCP connection of the RTSP protocol typically only contains the control messages, the number of messages being passed through here aren't that many (5 or 6 from each side if it is a simple request to start playback and, in the end, to end it). The big traffic will be handled through the UDP connections.
As such, it doesn't cause big performance issues if I unpack, manipulate, and repackage the messages that are being sent over TCP. So I just read the package, replace the necessary IP addresses as necessary and that's it. I also need to do this to read the UDP ports that the client and server negotiates so that my proxy can go in-between. Since the traffic over TCP is low, I'm able to do this.
My program uses sockets for inter-process communication. There is one server listening on a socket port(B) on localhost waiting for a list of TCP clients to connect. And on the other end of the server is another a socket(A) that sends out data to internet. The server is designed to take everything the TCP clients send him and forward to a server on the internet. My question is if two of the TCP clients happened to send data at the same time, is this going to be a problem for the server's outgoing socket(A)?
Thanks
The MSDN docs recommend that you use BeginSend and EndSend if multiple threads will be using the same socket to transmit data.
So I would suggest that you either use those methods or write outgoing data to a synchronized queue, from which a single thread will then pick data off of the queue and send it over socket(A)
You don't describe how you multiplex the traffic of multiple client streams onto a single outgoing stream. Just arbitrarily putting chunks of client traffic into the stream is guaranteed not the work. The receiving end on the opposite end of the intertube will have no idea what bytes belong to what conversation.
I'd recommend you focus on the opposite end first. What machine is out there, what does it do, what does it need to know about the multiple clients at the local end.
What makes more sense?
use one socket to send and receive data to/from a embedded hardware device
use one socket to send data and separate socket to read data
Communication is not very intensive but the important point is to receive data as fast as possible. Application works under Windows XP and up.
Sockets were designed for two way communication, so most likely the developers of the embedded device didn't design their system to work off two sockets.
I have some experience working with embedded hardware and I've seen them work various ways:
Device connects to your application and starts streaming data via UDP
In this scenario I've seen up to three sockets in play. One TCP listening socket that accepts a connection from the embedded device. The embedded device then sends through some connection parameters, such as how quickly it's going to send you the data. The embedded device then starts streaming data via upd. Once you've received the data you send a message down a second upd socket to say "I got that one". The device then starts streaming the next bit of data (again via upd). This then continues ad infinitum. I've seen variations where the initial TCP connection is skipped and device just constantly stream data.
Request/Response
How many sockets you'll need here depends on who's making the initial connection, as that'll determine who needs the listening socket. Since you're making the initial connection, I'll use that. This is the more connection oriented scenario. Here you make a connection to the device and request some data, the device then sends you the response to that data. In this scenarioyou can only use one socket. As the device will respond to each request on the socket it was received.
So to answer you question "What makes more sense?", it completely depends on the design of your embedded device. If it's responding on the same socket as you're requesting, the answer is simple as only one socket is possible. Streaming devices via upd should give better performance with two sockets, but again only if your device supports it.
As for the second part of your question, "to receive data as fast as possible.", that's easy go asynchronous. Here are some excellent blogs on asynchronous socket programming:
.NET Sockets - Two Way - Single Client (C# Source Code - Included)
.NET Sockets in Two Directions with Multiple Client Support (C# Source Code Included)
If you're using a custom/third party protocol to communicate with the device you can't go wrong having a read through these either:
How to Transfer Fixed Sized Data With Async Sockets
Part 2: How to Transfer Variable Length Messages With Async Sockets
Im no expert but is there any downside to just using one socket?
It can already send and receive and my guess is that you end up getting more overhead if you have one socket for reading and one for sending...