The actual problem is as follows:
There are two methods of getting a new worker: by creating a new child
or cloning from unused (UNKNOWN type) one.
Then creating a new one and serverlimit is not reached it work, if it
has been reached, it will be denied.
clone function uses the same base as the one used for creating a new one
except it reuses old child TYPE_UNKNOWN and problem is that ServerLimit
is checked before actually checking for free (TYPE_UNKNOWN) children and
if serverLimit has ever been reached in the past it will always fail.
Attached patch will fix this error.
To reproduce:
use 1 vhost. set
1 multiplexer
ServerLimit 5.
Maxprocessors >= 5.
IdleTimeout 10
exhaust all free slots.
wait 20s (over IdleTimeout) for children to go into TYPE_UNKNOWN state.
try to exhaust all slots again. Not possible.
Janno Sannik wrote:
There will be trouble if ServerLimit < MaxProcessors * Users
The problem is that then child is being terminated it's TYPE will be
marked as UNKNOWN and STATUS standby. If the same vhost want's to use it
whom it belonged it will work OK. But if someone else ( a vhost that
hasn't been active till now) needs to create a new processor/worker,
then it will hit the server limit, because childID's = NumServers.
This was tested by generating configuration file with 100+1(for status
monitoring, this will be the "poorly used" vhost) domains in it. with
every domain under different uid. Then we programmed a small bencmarking
utility which hammers apache with 100threads every thread randomizing
100 domain names. After hammering apache settled down and I was left
with 1 processor, 1 worker, 1 multiplexor and 319-2-100=217 STANDBY,
UNKNOWN children. Since this server status user had only one processor
at the time I started bencmark and ended it can't create any more
children since ServerLimit was allready reached.
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): CHECKING IF WE SHOULD CLONE A CHILD...
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): total_processors = 1, max_processors = 100
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): idle_processors = 1, min_free_processors = 3
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): CLONING CHILD
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_clone(): Trying to use more child ID's than NumServers. Increase
NumServers in your config file
Could these UNKNOWN children be reused by everyone somehow or to be
completely discarded so new ones can born?
I the mean time I look into perform_idle_server_maintenance(), since it
seems to be responsible for killing and starting children.
NameVirtualHost *
<IfModule peruser.c>
ServerLimit 320
MaxClients 320
MinSpareProcessors 3
MaxProcessors 100
MaxRequestsPerChild 1000
ExpireTimeout 7200
IdleTimeout 15
Multiplexer nobody nobody
</IfModule>
"poor vhost"
###### default #######
<IfModule peruser.c>
Processor apache
apache
</IfModule>
<Virtualhost *>
ServerAdmin [EMAIL PROTECTED]
DocumentRoot /home/system/apache/httpd.p1/default
ServerName default
ErrorLog /home/system/apache/httpd.p1/default_error.log
CustomLog /home/system/apache/httpd.p1/default_custm.log combined
<IfModule peruser.c>
ServerEnvironment apache apache
</IfModule>
<Location /sss>
SetHandler server-status
</Location>
</Virtualhost>
"1/100 vhost":
NameVirtualHost *
########## vhost1.kood.ee
##########
<Virtualhost *>
DocumentRoot /home/test/6001/vhost1
ServerName vhost1.domain
<IfModule peruser.c>
ServerEnvironment #6001 #6001
</IfModule>
</Virtualhost>
Debug:
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=0 child=1)
child_main(): sock_fd_in=212 sock_fd_out=213
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=0 child=1)
child_main(): PROCESSOR 1
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=0 child=1)
listen_clear(): function
entered
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=0 child=1)
listen_add(): function entered
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=0 child=1)
listen_add(): function entered
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): input available ... resetting socket.
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): receiving from sock_fd=212
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): recvmsg returned 449
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): trans_sock=93825040384080 fdx=6 sock_fd=6
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): header_len=432 headers="GET /sss
HTTP/1.1\r\nHost: 192.168.0.8\r\nUser-Age
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): header_len > 0, we got a request
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): There is no body
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
receive_from_multiplexer(): returning 0
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): CHECKING IF WE SHOULD CLONE A CHILD...
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): total_processors = 1, max_processors = 100
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): idle_processors = 1, min_free_processors = 3
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): CLONING CHILD
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_clone(): Trying to use more child ID's than NumServers. Increase
NumServers in your config file
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): marked jmpbuffer
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): calling process_socket()
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
process_socket(): Creating dummy connection to use the vhost lookup api
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
process_socket(): Looking up the right vhost
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
process_socket(): Base server is default, name based vhosts on
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
process_socket(): child_num=1 sock=93825040384080 sock_fd=6\n
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
process_socket(): type=PROCESSOR 1
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
peruser_process_connection(): function entered
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
peruser_process_connection(): leaving (DECLINED)
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
peruser_post_read(): PROCESSOR 1
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
peruser_post_read(): request for 192.168.0.8 / (server default) seems to
be for us
[Fri Aug 10 22:34:12 2007] [warn] (peruser: pid=18883 uid=48 child=1)
child_main(): returned from process_socket()
_______________________________________________
Peruser mailing list
[email protected]
http://www.telana.com/mailman/listinfo/peruser
--- httpd-2.2.3-clean/server/mpm/experimental/peruser/peruser.c 2007-08-13
09:41:41.000000000 +0300
+++ httpd-2.2.3/server/mpm/experimental/peruser/peruser.c 2007-08-13
11:43:11.644871624 +0300
@@ -1788,18 +1788,18 @@
child_info_t *this;
child_info_t *new;
- if(NUM_CHILDS >= server_limit)
- {
- _DBG("Trying to use more child ID's than NumServers. "
- "Increase NumServers in your config file.");
- return NULL;
- }
-
for(i = 0; i < NUM_CHILDS; i++)
{
if(CHILD_INFO_TABLE[i].pid == 0 &&
CHILD_INFO_TABLE[i].type == CHILD_TYPE_UNKNOWN) break;
}
+
+ if(i == NUM_CHILDS && NUM_CHILDS >= server_limit)
+ {
+ _DBG("Trying to use more child ID's than NumServers. "
+ "Increase NumServers in your config file.");
+ return NULL;
+ }
_DBG("cloning child #%d from #%d", i, my_child_num);
_______________________________________________
Peruser mailing list
[email protected]
http://www.telana.com/mailman/listinfo/peruser