Instantly  Increase ASP.NET Scalability - Thru ThreadPool
Each  time a request for a .NET resource (.aspx, page, .ascx control, etc.) comes in  a thread is grabbed from the available worker thread pool in the asp.net worker  process (aspnet_wp.exe on IIS 5.x, w3wp.exe on IIS 6/7) and is assigned to a  request. That thread is not released back into the thread pool until the final  page has been rendered to the client and the request is complete. 
Inside  the ASP.Net Worker Process there are Two Thread  Pools. The Worker Thread Pool handles all  incoming requests and the I/O Thread pool  handles the I/O (accessing the file system, web services and databases, etc.). 
But  how many threads are there in these thread pools? I had assumed that the number  of threads would vary from machine to machine – that ASP.NET and IIS  would carefully balance the number of available threads against available  hardware, but that is simply not the case. 
ASP.Net  installs with a fixed, default number of threads to play with: The CLR for the  1.x Framework sets these defaults at just 20 worker threads and 20 I/O thread  per CPU. 
Now  this can be increased by modifying the machine.config, but if you are not aware  of this, then 20 threads is all you’re playing with. If you have multiple  sites sharing the same worker process, then they are all sharing this same  thread pool. 
So  long as the number of concurrent requests does not exceed the number of threads  available in the pool, all is well. 
But  when you are building enterprise level applications the thread pool can become  exhausted under heavy load, and remember by default heavy load is more than  just 20 simultaneous requests. 
When  this happens, new requests are entered into the request queue (and the users  making the requests watch an hour glass spin). 
ASP.NET  will allow the request queue to grow only so big before it starts to reject  requests at which point it starts returning Error 503,  Service Unavailable. 
To resolve contention  problems, you can tune the following parameters in the Machine.config file to  best fit your situation: 
- maxWorkerThreads
- minWorkerThreads
- maxIoThreads
- minFreeThreads
- minLocalRequestFreeThreads
- maxconnection
- executionTimeout
To successfully resolve these  problems, take the following actions: 
- Limit the number of ASP.NET requests that can execute at the same       time to approximately 12 per CPU.
- Permit Web service callbacks to freely use threads in the       ThreadPool.
- Select an appropriate value for the maxconnections       parameter. Base your selection on the number of IP addresses and       AppDomains that are used.
Note The recommendation to limit the number of ASP.NET  requests to 12 per CPU is a little arbitrary. 
However, this limit has  proved to work well for most applications.
maxWorkerThreads and maxIoThreads
    ASP.NET uses the following  two configuration settings to limit the maximum number of worker threads and  completion threads that are used: 
<processModel maxWorkerThreads="20" maxIoThreads="20">
  The maxWorkerThreads  parameter and the maxIoThreads parameter are implicitly multiplied by  the number of CPUs. 
For example, if you have two  processors, the maximum number of worker threads is the following: 2*maxWorkerThreads
minFreeThreads and minLocalRequestFreeThreads
    ASP.NET also contains the  following configuration settings that determine how many worker threads and completion  port threads must be available to start a remote request or a local request:
<httpRuntime minFreeThreads="8" minLocalRequestFreeThreads="8">
If there are not sufficient  threads available, the request is queued until sufficient threads are free to make  the request. 
Therefore, ASP.NET will not  execute more than the following number of requests at the same time: (maxWorkerThreads*number of CPUs)-minFreeThreads
Note The minFreeThreads parameter and the minLocalRequestFreeThreads  parameter are not implicitly multiplied by the number of CPUs.
minWorkerThreads
    As of ASP.NET 1.0 Service  Pack 3 and ASP.NET 1.1, ASP.NET also contains the following configuration  setting that determines how many worker threads may be made available  immediately to service a remote request. 
<processModel minWorkerThreads="1">
  Threads that are controlled  by this setting can be created at a much faster rate than worker threads that  are created from the CLR's default "thread-tuning" capabilities. This  setting enables ASP.NET to service requests that may be suddenly filling the  ASP.NET request queue due to a slow-down on a back end server, a sudden burst  of requests from the client end, or something similar that would cause a sudden  rise in the number of requests in the queue. The default value for the minWorkerThreads  parameter is 1. We recommend that you set the value for the minWorkerThreads  parameter to the following value. 
minWorkerThreads = maxWorkerThreads / 2
  By default, the minWorkerThreads  parameter is not present in either the Web.config file or the Machine.config  file. This setting is implicitly multiplied by the number of CPUs. 
maxconnection
    The maxconnection  parameter determines how many connections can be made to a specific IP address.  The parameter appears as follows:
  <connectionManagement>    <add address="*" maxconnection="2">    <add address="http://65.53.32.230" maxconnection="12"></connectionManagement>  If the application's code  references the application by hostname instead of IP address, the parameter  should appear as follows:
<connectionManagement>    <add address="*" maxconnection="2">    <add address="http://hostname" maxconnection="12"></connectionManagement>  Finally, if the application  is hosted on a port other than 80, the parameter has to include the  non-standard port in the URI, similar to the following:
<connectionManagement>    <add address="*" maxconnection="2">    <add address="http://hostname:8080" maxconnection="12"></connectionManagement>
  The settings for the  parameters that are discussed earlier in this article are all at the process  level. However, the maxconnection parameter setting applies to the  AppDomain level. By default, because this setting applies to the AppDomain  level, you can create a maximum of two connections to a specific IP address  from each AppDomain in your process.
executionTimeout
    ASP.NET uses the following  configuration setting to limit the request execution time: 
<httpRuntime executionTimeout="90"/>    You can also set this limit  by using the Server.ScriptTimeout property.
  
  Note If you increase the value of the executionTimeout parameter,  you may also have to modify the processModel responseDeadlockInterval  parameter setting.
Recommendations
    The settings that are  recommended in this section may not work for all applications. However, the  following additional information may help you to make the appropriate  adjustments.
  If you are making one Web service call to a single IP address from each ASPX page,  Microsoft recommends that you use the following configuration settings:
- Set the values of the maxWorkerThreads       parameter and the maxIoThreads parameter to 100.
- Set the value of the maxconnection       parameter to 12*N       (where N       is the number of CPUs that you have).
- Set the values of the minFreeThreads       parameter to 88*N       and the minLocalRequestFreeThreads parameter to76*N.
- Set the value of minWorkerThreads to 50.       Remember, minWorkerThreads is not in the configuration file by       default. You must add it.
Some of these recommendations  involve a simple formula that involves the number of CPUs on a server. The  variable that represents the number of CPUs in the formulas is N. For these settings,  if you have hyperthreading enabled, you must use the number of logical CPUs  instead of the number of physical CPUs. For example, if you have a  four-processor server with hyperthreading enabled, then the value of N in the formulas will  be 8 instead of 4.
  
  Note When you use this configuration, you can execute a maximum of 12  ASP.NET requests per CPU at the same time because 100-88=12. Therefore,  at least 88*N  worker threads and 88*N  completion port threads are available for other uses (such as for the Web  service callbacks).
  
  For example, you have a server with four processors and hyperthreading enabled.  Based on these formulas, you would use the following values for the  configuration settings that are mentioned in this article. 
<system.web>               <processModel maxWorkerThreads="100" maxIoThreads="100" minWorkerThreads="50"/>               <httpRuntime minFreeThreads="704" minLocalRequestFreeThreads="608"/></system.web>  <system.net>               <connectionManagement>                               <add address="[ProvideIPHere]" maxconnection="96"/>               </connectionManagement></system.net>
  Also, when you use this configuration, 12 connections are available per CPU per  IP address for each AppDomain. Therefore, in the following scenario, very  little contention occurs when requests are waiting for connections, and the  ThreadPool is not exhausted: 
- The web hosts only one application (AppDomain).
- Each request for an ASPX page makes one Web service request.
- All requests are to the same IP address.
However, when you use this  configuration, scenarios that involve one of the following will probably use  too many connections: 
- Requests are to multiple IP addresses.
- Requests are redirected (302 status code).
- Requests require authentication.
- Requests are made from multiple AppDomains.
In  these scenarios, it is a good idea to use a lower value for the maxconnection  parameter and higher values for the minFreeThreads parameter and the minLocalRequestFreeThreads  parameter.
Also check this: Link - http://www.williablog.net/williablog/post/2008/12/02/Increase-ASPNET-Scalability-Instantly.aspx
Thanks & Regards,
Arun Manglick 
 
 
No comments:
Post a Comment