Po obstrzałem

Może zalazłem komuś za skórę, może dostałem rykoszetem jakiejś cyberwojny, a może po prostu jakiś script-kiddie postanowił sprawdzić, czy da się zablokować nikomu nie znany blog siedzący sobie spokojnie w zakątku Intenetu będącym odpowiednikiem schowka na miotły - nie wiem. Ale od jakiegoś czasu zacząłem dostawać powiadomienia, że strona xpil.eu nie odpowiada.

W ramach szukania przyczyny tego opłakanego stanu rzeczy zajrzałem do logu błędów Apacza i znalazłem tam informację, że mpm_prefork, moduł odpowiedzialny za uruchamianie dodatkowych sesji serwera www w razie potrzeby, dobił do maksimum liczby sesji i więcej nie uruchomi. Nie, bo nie. Westchnąłem ciężko ("cena sławy, co zrobisz, nic nie zrobisz") i zwiększyłem maksymalną ilość sesji dziesięciokrotnie. Zrestartowałem Apacza i już po chwili dostałem powiadomienie, że strona znów działa.

Ale dosłownie po trzech minutach przychodzi kolejne, że jednak nie działa.

Ki czort?

Zaglądam w logi - ten sam błąd.

Hmmm.

Ustawiłem sobie w cronie, żeby mi restartował serwer www co pięć minut i tyle. Podejście warte rolki taśmy hydraulicznej i puszki WD40 - ale działa.

Z tym, że jednak mnie trochę swędziało między drugim a trzecim neuronem. Noż kurdę, coś się przecież musi dać zrobić oprócz ordynarnego restartowania procesu, prawda?

Poguglałem zatem trochę bardziej szczegółowo... i się doguglałem. Otóż takie a nie inne zachowanie modułu mpm_prefork spowodowane jest najczęściej (A) nadmierną popularnością strony (nie grozi: pomimo 10 lat blogowania i ponad 2000 wpisów nadal mam odwiedzalność na poziomie 100 odsłon dziennie) lub (B) atakiem typu slowloris. Czyli, jak można wyczytać na Wiki, atakiem polegającym na wysyłaniu niekompletnych zapytań do serwera, który będzie cierpliwie czekał na ich skompletowanie, które jednak nigdy nie następuje. W efekcie serwer tworzy na bezdurno nowe wątki aż mu się wyczerpie pula - a potem głuchnie i ślepnie.

Na szczęście obrona przed tego typu atakiem jest dość prosta. Najpierw aktywujemy moduł mod_reqtimeout (u mnie był już aktywny - nie wiem, być może jest aktywowany domyślnie przy instalacji Apache), a potem w głównym pliku konfiguracyjnym Apacza (u mnie: /etc/apache2/apache2.conf) na samym końcu wstawiamy:

<IfModule mod_reqtimeout.c>
  RequestReadTimeout header=5-10,MinRate=5000 body=5-10,MinRate=5000
</IfModule>

Restartujemy serwer www i gotowe. Od tej pory nasz Apacz będzie automatycznie ubijał sesje, które wiszą podejrzanie długo, lub które mają podejrzanie niską prędkość transmisji.

Leave a Comment

Twój adres e-mail nie zostanie opublikowany.