かなり有名なmod_limitipconnですが、色々制限方法の記事をみていると、きっちりとその性能を説明できていないものが多い気がする。
あるディレクトリ以下又はファイルに対する同一IPからの同時接続数を制限するというのが、このモジュールの役目なんだが、大事なところが説明されていない。
例えば、よくある以下のような制限を行ったとする。
<Location /hoge>
MaxConnPerIP 3
</Location>
多くの情報ではこの設定だと、
[warning]
http://example.jp/hoge/index.cgi等、hoge/以下へのアクセスに対して、同一IPからの同時接続数を3に制限する。
[/warning]
とかかれていることが多い。
しかし、ここには大きな落とし穴がある。
実際にモジュールのソースをみると実装方法は、apacheのscoreboardを利用していて、server_limit(×thread_limit)分の全プロセスが処理しているrequestを全て調べ、そのrequestのclientのIPを調べて数え上げることで、同一IPからのrequestを制限している。
ソースでは、ap_hook_access_checkerのfook関数内で、以下のように実装されている。
/* Count up the number of connections we are handling right now from
* this IP address */
for (i = 0; i < server_limit; ++i) {
for (j = 0; j < thread_limit; ++j) {
ws_record = ap_get_scoreboard_worker(i, j);
switch (ws_record->status) {
case SERVER_BUSY_READ:
case SERVER_BUSY_WRITE:
case SERVER_BUSY_KEEPALIVE:
case SERVER_BUSY_LOG:
case SERVER_BUSY_DNS:
case SERVER_CLOSING:
case SERVER_GRACEFUL:
if (strcmp(address, ws_record->client) == 0)
ip_count++;
break;
default:
break;
}
}
}
ここで、scoreboard内に保存されている、現在のrequestの処理全てに対する、client(ソースIP)を調べている。
そして、アクセスしているIPとscoreboard内のclientがマッチした場合、IPカウントをインクリメントする。
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r,
"mod_limitipconn: vhost: %s uri: %s current: %d limit: %d",
r->server->server_hostname, r->uri, ip_count, cfg->limit);
if (ip_count > cfg->limit) {
ap_log_rerror(APLOG_MARK, APLOG_INFO, 0, r,
"Rejected, too many connections from this host.");
/* set an environment variable */
apr_table_setn(r->subprocess_env, "LIMITIP", "1");
/* return 503 */
return HTTP_SERVICE_UNAVAILABLE;
} else {
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r,
"mod_limitipconn: OK: Passed all checks");
return DECLINED;
}
最終的には、IPカウントと制限設定値(cfg->limit)を比較し、超えていれば503を返す。
つまり、ここに大きな落とし穴があり、limitipconnは、上記の設定だと、
[important]
/hoge以下にアクセスした場合は、/以下の全てのアクセスを含め、同一IPから同時に3リクエストまで処理を行う
[/important]
という制限になるのだ。
例えば、/hogeとは関係ない/fugaにある動画を3本ダウンロードしており、その状態で/hogeにアクセスすると、1アクセスすらできないのである。
上記のような実装の説明をした記事がなかなかなかったため、この記事で説明しておくこととする。
「mod_limitipconnの制限内容の落とし穴」への1件のフィードバック
コメントは受け付けていません。