Take the 2-minute tour ×
Server Fault is a question and answer site for system and network administrators. It's 100% free, no registration required.

I have written a Windows Network Service using C# which is designed to run on a Windows 7 machine. It is designed to be able to handle multiple requests in a single millisecond, which it seems to cope with in the most part, with no delay.
Occasionally, after every few thousand milliseconds, the server may experience a long delay of up to 40ms when, during which time the client has sent as many packets but not received a single response. Suddenly the server will wake up and respond to all requests within a couple of milliseconds (processing time for each request is in the region of 0.1ms).
How can I change my code or Windows Service settings to make the server more responsive? It would be better to minimise spikes of long delays (10ms is bearable, <5 is more reasonable, <1ms is the goal), but the regularity of delays is also a concern.

Thanks.


EDIT: The server machine I'm testing everything on is a laptop with a Core 2 Duo processor and SSD storage

share|improve this question
    
Does the problem exist on other machines the service is running on? Meaning is it consistent across machines? Windows has so many things running at once, that you may be fighting any number of things. My suggestion would be to slim down the Windows 7 install to only run the essentials to get what you are trying to accomplish done. By chance are you using the onboard NIC? you might try something with its own processing engine rather than relying on the Motherboard. Server NICs might be a good place to start. –  MikeAWood Sep 25 '13 at 6:22
    
Sorry, I've added some more details to the original post now. I'm using the onboard NIC but unfortunately don't have much testing time or hardware flexibility right now. Nevertheless, it would be good to know what hardware changes should be made so thanks for your suggestions (fresh Windows occurred to me, but not using a server NIC). –  user1585968 Sep 25 '13 at 6:31
    
You might to exclude the NIC from power management in bios/windows if possible too. With a laptop, you are likely just fighting the hardware. There are so many little tweaks for network adapters in windows that hopefully someone with tuning experience can jump in and offer up some help. I would start by running it on a known working good desktop and see if you see the same thing. –  MikeAWood Sep 25 '13 at 6:37
    
I'll definitely look into that; I always make sure the laptop is plugged in while testing at least. I'll see if I can shift over to a desktop at some point. –  user1585968 Sep 25 '13 at 7:14
    
Ryan's Answer has some good information, but I wont be surprised at all if it's a cheap NIC (Realtek, Marvel, or similar) and it's the culprit. Not sure what performance you require exactly, but companies like SolarFlare make a lot of money from high capacity (both low latency and high packet rate) NICs. –  Chris S Sep 25 '13 at 13:10

1 Answer 1

You're asking for extremely low and predictable latencies from a language with a garbage collector. The GC will pause your program for X milliseconds every Y interval while the GC thread runs.

You can use the Windows Performance Toolkit to verify this if you'd like.

You can tweak the garbage collector a bit with

GCSettings.LatencyMode = GCLatencyMode.LowLatency;

But it will still have to run eventually.

This is one reason you don't see a lot of blockbuster 3D games written in C#.

Tweak the GC if you want, but I think the best solution for this type of application is switching to native code.


You're also running on Windows 7, which is configured for shorter thread quantums than a Server OS, which means it context swtiches more often. (Ironically, this is so the machine feels 'snappier.')

You can change this with the setting 'Adjust for best performance of Background Services'. This is a system-wide setting, and is the setting for Windows Server. What it does is make the system's thread quantums longer, which means threads run long before another thread-scheduling decision is made, meaning fewer context switches. The idea being that with longer thread quantums, a server thread, once selected for execution by the thread scheduler, will be able to keep running for longer and have a better chance of finishing its work (i.e. servicing a client request) before being interrupted/preempted by another thread on the system.


Finally, if none of the above helps you, it may be something else. At this point you would want to analyze the system with the Windows Performance Toolkit, and you might find that the bursts of latency are actually caused by the NIC driver, the Windows Filtering Platform, something in the I/O stack... who knows.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.