prefork介绍

       一个进程处理一个请求;基于select()模型,所以最多一次创建1024个进程

    前缀pre在英语中的意思是预先的意思,那么在这里prefork的意思就是,预先创建进程的意思

    prefork采用的是预派生子进程方式,用子进程处理不同的请求,每个请求对应一个子进程,进程之间是彼此独立的。当apache启动后会先启动StartServers个子进程,等待1秒后会再创建两个,再等待1秒后创建4个,再一秒后创建8个这样直到创建满MinSpareServers个子进程为止,那么此时MinSpareServers个子进程会待命,这种待命模式不必在新请求到来时重新创建, 一定程度上加快了进程的响应速度。

     MaxSpareServers的值代表最大的待命进程数,如果待命进程数大于这个apache会自动kill掉多余没有启用的进程。如果站点负载交大,内存足够多, 那么可以考虑加大MinSpareServers和MaxSpareServers一般来说一个子进程大概占用2-10M左右。

     MaxRequestWorkers (在之前的版本中称之为MaxClients),此参数很重要, 其表示apache可以同时处理请求数,默认值是250,我们一般都会将其加大很多, 但是不能大于250岂不是很坑爹? 别担心,apache同时提供了另一个指令ServerLimit,将这个指令和MaxRequestWorkers设置相同即可,该指令用于修改apache默认256的限制,ServerLimit 的最大硬限制为200000,也就是说理论上我们可以让apache同时处理20万的请求,至于这20万请求过来之后apache是如何分配的就要看你的其他参数的设置了。
   MaxRequestsPerChild上面说到都是进程, 那么这个MaxRequestsPerChild就代表的是每一个进程所能够承受的最大请求数量,如果某一个进程超过了这个数量则进程自动释放所有内存然后自杀掉。此值可以设置为0,0就是说永远不结束,这样做的弊端是进程占用内存过大而且容易内存溢出。不过对于KeepAlive链接, 只有第一个请求会被算进去,KeepAlive有效期类的其他请求将不作数。


Apache2.2版本prefork参数:

  <IfModule prefork.c>
      StartServers       8    #默认启动的工作进程数;启动时开启的进程数
       MinSpareServers     5    #最少空闲进程数,保存备用;备用进程的最小数目
     MaxSpareServers     20    #最大空闲进程数,保存备用;备用进程的最大数目
      ServerLimit       256    #最大活动进程数               
     MaxClients        256    #并发请求的最大数
     MaxRequestsPerChild   4000    #每个子进程在生命周期内所能够服务的最多请求个数;
        #合理配置此参数可以有效避免apache服务器内存溢出
   </IfModule>
   注意:虽然MaxRequestsPerChild缺省设为0可以使每个子进程处理更多的请求,但如果设成非零
       值也有两点重要的好处:
   1、可防止意外的内存泄漏。
   2、在服务器负载下降的时侯会自动减少子进程数。因此,可根据服务器的负载来调整这个值。

Apache2.4版本prefork参数:

   <IfModule mpm_prefork_module>   #如果mpm_prefork_module这个模块被启用
     StartServers        5  #启动时开启的进程数
     MinSpareServers      5   #最少空闲进程数,保存备用;备用进程的最小数目
     MaxSpareServers       10  #最大空闲进程数,保存备用;备用进程的最大数目
     MaxRequestWorkers     250 #并发请求的最大数
     MaxConnectionsPerChild   0   #每个子进程在生命周期内所能够服务的最多请求个数;
   </IfModule>

Worker介绍:

    worker模型:主进程生成多个进程,每个进程生成多个线程;

    worker的工作原理是:由主控制进程生成“StartServers”个子进程,每个子进程中包含固定的ThreadsPerChild线程数,各个线程独立地处理请求。同样,为了不在请求到来时再生成线程,MinSpareThreads和MaxSpareThreads设置了最少和最多的空闲线程数;而"MaxClients"设置了所有
子进程中的线程总数。如果现有子进程中的线程总数不能满足负载,控制进程将派生新的子进程。
    "MinSpareThreads"和"MaxSpareThreads"的最大缺省值分别是75和250。这两个参数对Apache的性能影响并不大,可以按照实际情况相应调节。"ThreadsPerChild"是workerMPM中与性能相关最密切的指令。这个指令设置了每个进程建立的线程数。子进程在启动时建立这些线程后就不在建立新的线程了。每个进程所拥有的所有线程的总数足够大,以便可以处理可能的请求高峰。worker模式下所能同时处理的请求总数是由子进程总数乘以"ThreadsPerChild"值决定的,应该大于"MaxClients"。如果显式声明了"ServerLimit",那么它乘以ThreadsPerChild的值必须大于等于"MaxClients",而且"MaxClients"必须是"ThreadsPerChild"的整数倍,否则Apache将会自动调节到一个相应值(可能是个非期望值)。


Apache2.2版本的worker模型参数:

<IfModule worker.c>
          StartServers         4        #启动的子进程的个数
          MaxClients         300        #并发请求的最大数
          MinSpareThreads     25        #最小空闲线程数
          MaxSpareThreads     75        #最大空闲进程数
          ThreadsPerChild     25        #每个进程可以生成的线程数
          MaxRequestsPerChild  0        #每个进程在生命周期内所能够服务的最多请求个数;
              #0,表示无限制;
        </IfModule>

Apache2.4版本的worker模型参数:

<IfModule mpm_worker_module>
        StartServers             3      #启动的子进程的个数
        MinSpareThreads         75      #最小空闲线程数
        MaxSpareThreads        250      #最大空闲进程数
        ThreadsPerChild         25      #每个进程可以生成的线程数
        MaxRequestWorkers      400      #并发请求的最大数        
        MaxConnectionsPerChild   0      #每个子进程在生命周期内所能够服务的最多请求个数;
            #0,表示无限制
</IfModule>

prefork和work的比较:


    prefork模式使用多个子进程,每个子进程只有一个线程。 每个进程在某个确定的时间只能维持一个连接。在大多数平台上,Prefork MPM在效率上要比Worker MPM要高,但是内存使用大得多

    prefork的无线程设计在某些情况下将比worker更有优势:它可以使用那些没有处理好线程安全的第三方模块,并且对于那些线程调试困难的平台而言,它也更容易调试一些。
    缺点:多进程的惊群问题,简单来说多进程服务(例如Apache)在一个请求发送时候会唤醒所有sleep的进程,但是最终服务的只有一个,在进程数目很多,请求频繁的时候这会造成一个大困扰,系统会忙于切换进程,如果看Top会发现CPU使用在system的比例很高。

    worker模式使用多个子进程,每个子进程有多个线程。 每个线程在某个确定的时间只能维持一个连接。通常来说,在一个高流量的HTTP服务器上,Worker MPM是个比较好的选择,因为Worker MPM的内存使用比Prefork MPM要低得多。

    但worker MPM也由不完善的地方,如果一个线程崩溃,整个进程就会连同其所有线程一起”死掉.由于线程共享内存空间,所以一个程序在运行时必须被系统识别为”每个线程都是安全的”。

    总的来说,prefork方式速度要稍高于worker,然而它需要的cpu和memory资源也稍多于woker。