I don't have your code or your server but here are some things to check based on your post and response to my comment:
1) You have quite a lot of (presumably active) processes running. A process is an expensive thing compared to an
AppDomain
or a thread. When switching between threads the kernel also has to switch address spaces if the new thread is from a different process (highly likely with 200 active processes). In the Task Manager check "View > Show Kernel Times" and see how much of that processor % is being used for the kernel. Consider using
AppDomain
s to see if your problem is resolved. If not, consider a threading (pool) approach. Generally I use the rule "processes < AppDomains < threads". Choose the highest on the list that meets your requirements because the lower you go the more overhead is incurred.
2) Reducing the number of processes would also allow you to bundle up SQL statements and batch execute them. Probably not your issue unless you're running the 200 processes and the DB on the same machine but a nice bonus nonetheless.
3) Debug and determine memory usage, ensure different processes aren't fighting over resources (DB access for example), and just give your code a once-over for good measure. From 5-10% at 50 to 10% at 100 with a threshold of 120-125 until you jump to 100% sounds like you're dealing with overloading some part of the system itself but you never know.
4) Strings can be ugly things to handle en masse. It may simply be that your program is handling them inefficiently and chewing up memory or forcing the GC to run frequently.
This[
^] is a good basic primer on how strings are handled in C#.