아파치웹서버에서의장애시대처방법 시스템관리자는시스템에대해보수적이어야한다는말이있다. 이 보수적 이라는말은특정한정치적성향을뜻하는것이아니라시스템에대해단 1% 라도문제가될수있는여지를제거하고, 각유저에게는불편함을주지않는한도내에서가급적사용권한을제한하여혹시나있을지모를시스템의침해나크래쉬등에대비하는것을뜻한다. 아울러새로운룰을적용또는변경하거나프로그램을새로이도입할때에도이프로그램으로인하여다른문제가발생할수있는여지는없는지여부를신중히검토후도입하여야한다. 따라서이번호에서는아파치웹서버를운영해오면서서버관리자라면누구나접할수있는여러가지장애와이에따르는원인과해결방법을찾아보도록하겠다. 오늘과내일넷센터홍석범 (antihong@tt.co.kr) 장애 1. 접속이갑자기느려지거나아예접속이안될때가끔접속자가많은서버를운영하다보면갑자기웹접속이되지않거나접속이너무느려아파치데몬개수를확인해보면 httpd 가 256 개나떠있는경우가있다. 기본적으로아파치웹서버의경우 MaxClients 가 256 으로설정되어있어동시에 256 개의데몬이뜨게되면더이상의접속을받아들이지않고, 기존의프로세스가죽을때까지대기한후접속이끊기게되면그제서야접속을받아들이게된다. 따라서동시접속이많은경우에는이전의웹접속이끊길때까지대기를하여야하므로접속속도가느린것처럼느끼게되는것이다. 일반적으로정상적인접속의경우에 256 개의프로세스가모두뜨는경우는그리많지않기에현재의상태가비정상적인접속인지여부를판단하여야한다. 이를판단할수있는방법은 netstat na grep ES 로 ESTABLISHED 된연결상태를확인하여클라이언트의 IP 가정상적인연결인지여부를확인하면된다. 또는 netstat -na grep ES awk '{print $5}' sort 로클라이언트의 IP 만따로 Sort 하여확인하여보도록한다. 통상적으로 HTTP 1.1 규약에서부터적용되기시작한 KeepAlive 기능을지정하였을경우한클라이언트 IP 에서동시에 3-5 개정도의 http 프로세스를생성하므로한 IP 에서 3-5 개정도의프로세스를생성하는것은정상적인현상이다. 비정상적인접속의경우에는아래와같은이유가있을수있다. (1) 서비스거부공격 (DoS) 의경우동시에서비스할수있는프로세스의한계가있다는점을악용한서비스거부공격일가능성이있다. 이미한번의실행으로 100 개나 200 개등원하는만큼의동시접속을맺은후이접속을끊지않고유지할수있는공격코드가인터넷상에공개되어있다. 그러나이러한공격의경우공격지의 IP 를속이기가매우어려우므로 netstat 으로확인후비정상적인접속으로확인시해당 IP 를차단하면된다.
특정 IP 의라우팅을차단하는방법은아래와같이 route 를이용한방법과 iptables ( 커널 2.4 이상 ) 를이용한방법이렇게두가지가있다. 예 ) 공격지 IP 인 211.40.4.6 으로부터의라우팅을차단하는설정 # route add host 211.40.4.6 reject # iptables A INPUT s 211.40.4.6 j DROP 실제적용되었는지확인하는방법은각각 route n 과 iptables L n 이다. 참고로 TCP SYN Flooding 공격의경우 SYN 패킷만대량으로발송할뿐 ESTABLISHED 상태가되지않으므로 TCP SYN Flooding 공격과는무관하다. (2) include 를잘못하여무한루프가돌경우요즘에는 php 와 mysql 을연동하여많이사용하고있는데, 프로그래밍과정에서의실수로 php 파일에서같은 php 파일을 include 하는경우가있다. 또는 a.php 파일에서 b.php 파일을 include 하고 b.php 파일에서다시 a.php 파일을 include 하는경우도그러한경우일것이다. 이러한경우에는무한루프가돌게되어결국은아파치데몬이금새 Maxclients 에서지정한개수로차버리게되는데, 어떤파일에서무한루프가돌고있는지찾기가힘들다. 따라서임시로아래와같이 include 를하지못하도록차단을하는방법이있다. # iptables A INPUT -p tcp -i lo -s xxx.xxx.xxx.xxx --sport 1024:65535 -j DROP 이는같이서버내에서 include 시에는 lo (Lookback Interface) 를통해 sport 가 1024 이후의 high port 를이용하여통신한다는특성을이용한것이다. 그러나이설정을하였을경우로컬서버에서클라이언트포트를전혀사용할수없게되므로다른서비스에도장애가되기때문에임시로만사용하기바란다. 또는 ps aux grep http 로보이는프로세스에서 ls la /proc/pid/ 로각각의 http 프로세스가어떤파일을참조하고있는지일일이추적하는방법도있다. ( 예 :cwd -> /home/user1/public_html/infinite_loop/) 정상적인접속의경우에는아래와같이대처한다. (1) KeepAlive 옵션변경기본값으로설정되어있는 KeepAlive On 을 KeepAlive Off 로변경후아파치를재시작한다. KeepAlive 는 HTTP 1.1 규약에서부터적용된것으로접속속도에큰영향을준다. KeepAlive 를 Off 로설정시다소접속속도는떨어지지만좀더많은동시접속을수용할수있다. 따라서 MaxClients 에도달할정도로동시접속자가많은경우에는 KeepAlive 를 Off 로설정하는것이다소임시방편이기는하지만해결방법이될것이다.
KeepAlive 설정에대해서는 Hit 의개념과관련지어이해하면된다. 예를들어 10 개의이미지파일을링크한 HTML 페이지를로딩시웹브라우저는이 HTML 파일을다운로드하여클라이언트에서파싱 (parsing) 을하면서이미지파일등이링크되어있을경우서버에접속하여이미지파일을요청하는데, KeepAlive 가 On 일경우에는한번맺은 TCP 연결에대해같은 Client IP 에서접속이있을것이라가정하고기존의프로세스가대기하고있다가이후의접속을처리하기때문에다시접속을맺는절차가필요없이빨리서비스가가능하지만, KeepAlive 가 Off 인경우에는이미지파일을불러올때마다매번세션을새로맺고끊는과정을반복하여야하기때문에속도가느려질수밖에없다. 아파치홈페이지의문서에의하면많은이미지파일이있는 HTML 문서를로딩시 KeepAlive 설정에따라최고 50% 까지속도차이가날수있다고한다. 그렇다고해서모든사이트에서 KeepAlive 를 On 으로하는것이좋은것이아니다. 순간적인동시접속자는많지만한두번검색후검색결과의링크를따라다른사이트로빠져나가는검색엔진의경우에는 KeepAlive 를 Off 로하는것이유리할것이다. KeepAlive 를 On 으로설정하여그대로사용할경우에는 15 초로설정된 KeepAlive Timeout 을 15 초에서 5초정도로낮게설정하는방법도있으며이값은자신의시스템환경에맞게적절히설정하기바란다. (2) 아파치의 MaxClients 조절기본적으로는 256 으로설정되어있는 MaxClients 의한계를 512 나 1024 와같이적절히변경한다. 그러나이값을변경하기위해서는아파치의소스를수정후다시컴파일하여야하므로아파치의소스디렉토리에있는 src/include/httpd.h 파일에서 HARD_SERVER_LIMIT 256 로설정된값을 512 나 1024 로변경후아파치를재컴파일하면된다. 만약커널 2.2.X 일경우에는 /usr/src/linux/include/linux/tasks.h 에서 NR_TASKS 와 MAX_TASKS_PER_USER 변수역시수정한후커널을재컴파일해주어야하며, 2.4.X 의경우에는관련된커널제한이없어졌으므로아파치만재컴파일하면된다. 그러나대부분의사이트에서는 256 정도로설정되어도충분히서비스가가능하므로무작정이값을크게늘려메모리를낭비할필요가없으니특별한경우가아니라면이값을늘리지않는것이좋다. (3) 추가아파치데몬설정만약여러도메인중특정도메인이나어떠한사이트내특정컨텐츠의접속이특별히많아같은서버에있는다른사이트에까지피해를주고있다면이부분을별도로데몬을띄워서비스하는방법도있다. 이를테면한사이트에서게시판의접속이매우많다면기존의 80 번포트외에 8080 과같은임의의포트로작동하는웹데몬을추가로띄워이포트를통해접속이많은서비스를담당하게하는것이다. 이를위해서는기존의 httpd.conf 파일을 httpd8080.conf 와같이설정파일을복사후 httpd8080.conf 파일을아래와같이변경하면된다.
port 80 port 8080 User nobody User www Group nobody Group www 그리고 /usr/local/apache/bin/httpd f /usr/local/apache/conf/httpd8080.conf 와같이실행하면 8080 포트로작동하는웹서버데몬을추가로띄우게되는것이다. 물론이때 www 라는계정은서버에생성되어있어야하며 Nobody 가아닌 www 라는별도의계정으로데몬을작동하는이유는한유저 (nobody) 가생성할수있는프로세스의한계가있기때문이며커널 2.4.X 에서는이제한이없으므로 Nobody 로작동해도관계없다. 또는기존의웹데몬인 httpd 와파일이름을다르게하여서로구별을쉽게하기위해 httpd 대신 httpd8080 등다른이름으로변경하여실행하여도좋다. 웹접속은 http://domain.com:8080/ 으로하면되며이러한방식으로 8081, 8082, 8083. 등의여러포트를띄울수있다. 실제로얼마전필자가운영하는호스팅서버에서특정사이트의게시판의접속이폭주하여모든웹접속이느려진적이있었는데, 위와같이게시판부분만따로떼어 8080 포트로분리하여서비스를하여문제를해결한적도있다. 장애. 프로세스가과도한메모리를사용할경우. 특별히이상한프로세스는없는데, 시스템의부하가갑자기올라가는경우가있다. 심할경우에는콘솔에서키작동이되지않아제어자체가불가능한경우도있는데, 이러한경우에는어쩔수없이시스템 reboot 밖에방법이없다. 이는의도적이든그렇지않든유저가 cgi 나 php 등의프로그램을잘못짜서과도한메모리를소모하는프로세스를실행하기때문인경우인데, 실제로시스템의메모리를많이소모하는프로그램을짜는것은단몇줄의코드로도가능하다. 아래와같이메모리를소모하는간단한 C 코드를작성해보자. 참고로스크립트키드의악용을막기위해코드중일부를변경하였다. /* memory.c */ #include <unistd.h> #include <stdlib.h> void html_content(void); int main() {
char *some_memory; int size_to_allocate = ONE_K; int megs_obtained = 0; int ks_obtained = 0; html_content(); printf("program Executed!!!<p>"); } while (1) { for (ks_obtained = 0; ks_obtained < 1024; ks_obtained++) { some_memory = (char *)malloc(size_to_allocate); if (some_memory == NULL) exit(exit_failure); sprintf(some_memory, "Hello World"); } printf("now allocated %d Megabytes<br>\n", megs_obtained); } exit(0); void html_content(void) { printf("content-type: text/html\n\n"); } 작성후 gcc o memory.cgi memory.c 로컴파일한후이파일을 http://domain.com/memory.cgi 와같이웹에서실행해보도록하자. 아무리메모리와 CPU 가많은시스템이라하더라도이프로그램을실행하자마자거의통제불능상태로되어결국시스템재부팅을하게될것이다. 이렇듯이메모리를무한정소모하는것을차단하기위해서는아파치의설정인자 (Directive) 중에서 RLimitMEM 을사용하여차단할수있다. 이인자는아파치웹서버에서생성된특정프로세스가작동시소요가능한최대메모리의양을제한하는것으로메모리를많이소모하는 CGI 가작동할때이인자에서지정된메모리까지만실행이되고그이상소요시에는더이상작동하지않도록해준다. 예를들어 httpd.conf 에
RLimitMEM 20480000 21504000 <Directory /home/special/public_html/*> RLimitMEM 51200000 52224000 </Directory> 와같이설정하였다면모든디렉토리에서는메모리를 20 메가나최대 21 메가까지만사용이가능하고 /home/special/public_html/* 디렉토리이하에접근시에는특별히 50 메가까지메모리이용이가능하게된다. 실제로위와같이설정후 memory.cgi 를웹에서호출하면아래와같이일정량의메모리만사용되고중단하는것을확인할수있다. 이와비슷한인자로 CPU 점유율을제한하는 RLimitCPU 와사용자당프로세스의개수를제 한할수있는 RLimitNPROC 이있으며이에대해서는 http://httpd.apache.org/docs- 2.0/mod/core.html 를참고하기바란다.
장애. 큰사이즈의파일을업 / 다운로드하여부하가유발될경우 누구나업로드나다운로드가가능한자료실을운영하고있을경우사이즈가너무큰파일을업로드또는다운로드할경우부하가많이걸리게되어결국시스템의성능저하를유발하게된다. 최근배포되는게시판 / 자료실프로그램에서는대부분업로드할수있는용량등을제한할수있는기능이있지만그렇지않은프로그램도상당수있어웹서버차원에서이제한을적절히설정할필요가있다. 아파치에서는이와관련하여웹서버에서업로드 / 다운로드할수있는파일의사이즈를제한하는 LimitRequestBody 기능을이용할수있다. LimitRequestBody 는클라이언트가요청시 http 프로토콜을통해서버가제공할수있는메시지의크기를 byte 단위로정의하는것으로무한대를의미하는 0 부터 2,147,483,647(2Giga) 까지설정가능하며이설정으로대용량의파일을업 / 다운로드하는형태의서비스거부공격을차단할수있다. 이를설정하는방법은 httpd.conf 를열어아래의라인을추가하면된다. <Directory /> LimitRequestBody 7168000 </Directory> <Directory /home/special/> LimitRequestBody 10240000 </Directory> 위와같이 LimitRequestBody 인자를설정하면아파치웹서버를이용하여업 / 다운로드하는모든파일의사이즈를 7M 로제한하고 /home/special/ 이하에대해서는 10M 로제한하게된다. 위와같이설정시지정된사이즈를초과하는파일을업로드 / 다운로드시에는아래그림과같은에러메시지가뜨며업로드 / 다운로드가되지않는다.
장애. 특정한이름의파일을실행하지못하도록하고자할때 최근에는대부분의사이트들이대화방 ( 채팅 ) 을위해자바로프로그래밍된자바대화방을사용하는추세이지만얼마전까지만하더라도 C 나 Perl 로된 CGI 대화방을설치하여사용하는것이유행이었다. 그런데, 이대화방의경우대화방에참여하는유저중한명이글을입력할경우모든유저에게이내용이실시간으로뿌려주어야하는특성상시스템의메모리를매우많이소모하는대표적인프로그램중하나였다. 따라서채팅 CGI 프로그램을원천적으로사용할수없도록하는방법을고민하게되었는데, 해결방법은대부분의채팅프로그램이 xxxchat.cgi 또는 chatxxx.cgi 라는파일을실행파일이름으로한다는특징을이용하면된다. 즉, httpd.conf 를열어아래와같이설정하면파일명에 chat 이라는단어가포함된 CGI 파일은작동하지않게되는것이다. <Files "*chat*.cgi"> Order allow,deny Deny from all
</Files> 이러한방식으로특정한파일에대해웹에서의접근을차단할수있다. 따라서 CGI 파일에아무리소유권과실행권한을주었다하더라도웹서버자체에서접근을거부하였으므로웹에서접근하면 Forbidden 에러가나게된다. 이러한식으로특정파일이름을가진파일의실행이나접근을차단할수있다. 장애. 검색로봇의접근을차단하고자할때 갑자기특정한 IP 주소에서짧은시간에많은접속을하여시스템의부하가올라가웹접속 로그를살펴보니아래와같이이해할수없는내용이남는경우가있다. 211.51.63.4 - - [26/Sep/2001:22:19:42 +0900] "GET /robots.txt HTTP/1.0" 404 285 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /index.asp HTTP/1.0" 404 284 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /index.php HTTP/1.0" 404 284 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /index.php3 HTTP/1.0" 404 285 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /default.htm HTTP/1.0" 404 286 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /default.html HTTP/1.0" 404 287 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /default.asp HTTP/1.0" 404 286 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /default.php HTTP/1.0" 404 286 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /default.php3 HTTP/1.0" 404 287 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /main.htm HTTP/1.0" 404 283 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /main.html HTTP/1.0" 404 284 211.51.63.4 - - [26/Sep/2001:22:19:43 +0900] "GET /main.asp HTTP/1.0" 404 283 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /main.php HTTP/1.0" 404 283 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /main.php3 HTTP/1.0" 404 284 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /home.htm HTTP/1.0" 404 283 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /home.html HTTP/1.0" 404 284 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /home.asp HTTP/1.0" 404 283 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /home.php HTTP/1.0" 404 283 211.51.63.4 - - [26/Sep/2001:22:19:44 +0900] "GET /home.php3 HTTP/1.0" 404 284 무작위로 index.php index.asp, index.php3, default.html, default.asp 등의파일을순서대로요청하는것으로보아검색엔진일가능성이높다고가정할수있다. 특히 robots.txt 파일을요청하는것으로검색엔진이라고장담할수있을것이다. httpd.conf 에서 Logformat 를 common 대신 {User-agent} 변수를추가하여정의하면
서버에접근하는 agent 정보도알수있는데, UA(User Agent) 는일반적인웹브라우저뿐만아니라검색로봇이나방랑로봇등웹서버에접속하여웹페이지를가져오거나해석하는모든종류의프로그램을뜻한다. 이는흔히사용하는 Internet Explorer나 Netscape 등의브라우저외에도 lycos의 spider 나 AltaVista의 Scooter와같은검색로봇과 Teleport 나 WebZIP, GetRight 등오프라인브라우저모두 UA의범위에속한다. 검색로봇이어떤사이트를방문하여문서를인덱싱하거나오프라인브라우저가페이지를한꺼번에요청하여긁어가는것은일반사용자가웹브라우저로서버에접속하여원하는페이지를보는일반적인경우와그성격이다르다. 여러페이지를동시에요청하는정도를벗어나아예한웹사이트의모든페이지를짧은시간에통째로긁어가기도하기때문에이러한경우에는서버에매우많은프로세스를생성하면서웹서버의로드가크게올라가게되는것이다. 특히 DB와연동하는사이트의경우에는심할경우정상적인서비스를하지못할정도이다. 모든사이트가검색엔진에등록될필요는없거나또는허용된일부유저만접근이가능한페이지의경우로봇의접근을차단할필요가있으므로이러한경우에는아래와같이설정된 robots.txt 파일을웹서버의최상위 / 디렉토리에두면모든검색로봇이 /secure 디렉터리를인덱싱하지않는다. User-agent: * Disallow: /secure "User-agent: *" 는모든로봇를대상으로한다는것을뜻하며예를들어 AltaVista Scooter 등특정한 UA 에대해서만설정하고싶다면다음과같이하면된다. User-agent: scooter 검색로봇과관련된더자세한정보를얻기원한다면아래의사이트를참고하기바란다. http://info.webcrawler.com/mak/projects/robots/robots.html http://info.webcrawler.com/mak/projects/robots/norobots.html 아울러웹서버에서특정한 User-Agent 의접근을차단하고자한다면 httpd.conf 에아래와같이 BrowserMatch 를사용하여설정해도된다. BrowserMatch "WebZIP" go_out BrowserMatch "Teleport" go_out BrowserMatch "GetRight" go_out BrowserMatch "WebCopier" go_out BrowserMatch "NetZip Downloader 1.0" go_out BrowserMatch "NetZip-Downloader/1.0.62" go_out BrowserMatch "Teleport Pro/1.29" go_out BrowserMatch "Teleport Pro/1.24" go_out BrowserMatch "Teleport Pro/1.26" go_out <Directory /home/no-ua/> Options Includes ExecCGI
AllowOverride None Order allow,deny Allow from all Deny from env=go_out </Directory> 위와같이설정시에는 /home/no-ua/ 디렉토리이하에대해서는 go_out 이라는변수에지정한 WebZip 이나 Teleport 등 UA 프로그램의접근을차단하게된다. 다른 UA 도차단하고싶으면위와같이웹서버의로그를살펴보아 agent 정보에남는 UA 를 go_out 으로추가해주면된다. 같은방식으로만약특정디렉토리이하에대해서 MSIE 브라우저로접근하지못하도록설정한다면어떻게하면될까? 아래와같이 BrowserMacth 를이용하여설정하면 agent 정보에 MSIE 라설정되는 UA 는차단될것이다. BrowserMatch "MSIE" msie <Directory /> Options Includes ExecCGI AllowOverride None Order allow,deny Allow from all Deny from env=msie </Directory> 최근에는각종로봇이버전을새롭게하며계속적으로나오고있으므로지속적으로로그를살펴보아접근통제를하고자하는 UA 를설정하는것이좋다. 장애. 외부에서데이터를무단링크하여부하가유발될때 최근에와레즈사이트를통해게임이나오락, 동영상등각종데이터들이공유되면서와레즈사이트에서관련없는임의의서버에데이터를업로드한후무단링크하여서비스하는경우가많다. 이러한경우데이터전송량이갑자기늘어서버의부하가급격히올라감은물론한정된회선의대역폭도소모하게되어서버를관리하는관리자들에게는이러한무단링크가큰골치거리중에하나이다. 대부분의무단링크가대용량이기때문에이를차단하기위해위와같이 LimitRequestBody
를이용하여임의의용량이상의데이터에대한업 / 다운로드용량을제한하는방법도있지만아래와같이 BrowserMatch 대신 SetEnvIFNoCase Referer 를이용하는방법도있다. SetEnvIFNoCase Referer "warez" link_deny SetEnvIFNoCase Referer "free" link_deny SetEnvIFNoCase Referer "home" link_deny <FilesMatch "\.(avi mpe?g zip asf exe)$"> Order allow,deny allow from all deny from env=link_deny </FilesMatch> 위와같이설정시에는 Referer 이 warez 또는 free 나 home 이포함되었을경우이사이트를 link_deny 라는변수에할당하고, 환경변수가 link_deny 일때는확장자가 avi 나 mprg,zip,asf 등인파일에대한 access 를제한하고있다. 따라서홈페이지주소에 warez 나 free 또는 home 이포함된주소에서위의데이터를무단링크하였을경우에는이를차단할수있다. Nocase 를추가로설정하였을경우에는대소문자를가리지않아링크하는사이트가대소문자에관계없이 http://my.warez.org/ 나 http://my.warez.org/ http://my.warez.org/ 모두적용된다. 다른확장자를추가하고나설정을변경하고자할경우에는정규식 (Regurar Expression) 을이용하여설정하면된다. 또는이와는반대로아예 httpd.conf 에서아래와같이설정할수도있다. <VirtualHost tt.co.kr> ServerAdmin webmaster@tt.co.kr DocumentRoot /home/tt/public_html ServerName tt.co.kr ServerAlias www.tt.co.kr SetEnvIf Referer tt\.co\.kr link_allow SetEnvIf Referer www\.tt\.co\.kr link_allow SetEnvIf Referer ^$ link_allow <FilesMatch ".(mpg asf wmv)$") Order Deny,Allow Allow from env=link_allow Deny from all </FilesMatch>
</VirtualHost> 위와같이설정하였을경우외부에서는 mpg, asf, wmv 확장자를갖는파일에대해서는일체의무단자료링크가불가능하게되며오직 link_allow 에서지정한도메인에서만링크가가능하게된다. 위와같이설정후외부에서무단링크를하였을때 error_log 를살펴보면아래와같이무단으로링크한자료의다운로드가작동하지않는것을확인할수있다. [Tue Sep 4 15:55:44 2001] [error] [client 211.230.82.78] client denied by server configuration: /home/tt/public_html/data/3-2.wmv 장애. 아파치데몬은떠있는데, 접속이되지않는경우 분명데몬은정상적으로떠있고 MaxClients 에도달하지도않았는데, 실제로접속이되지않는경우가있다. 이러한경우라면웹서버가 TCP SYN Flooding 공격을받고있을가능성이있다. netstat na grep SYN 으로확인하여많은 SYN_RECEIVED 프로세스가보인다면이공격때문이며이러한경우에는 # sysctl w net.ipv4.tcp_syncookies=1 또는 # echo 1 > /proc/sys/net/ipv4/tcp_syncookies 로 syncookies 기능을 enable 하면된다. Syncookie 기능은일단커널에서지원되어야하므로이설정이적용되지않으면커널에서의설정여부를확인해보아야한다. 이공격에대한보다자세한내용은본지 7월호에실린 TCP SYN Flooding 공격의원인과해결책 을참고하기바란다. 장애. 코드레드나 Nimda 등의웜공격으로로그파일의 크기가커질때 최근에코드레드와 Nimda 등 Windows NT/2000 기반의 IIS 를공격하는무차별적인웜공격으로인하여부하가유발되고로그파일이불필요한데이터로채워지는경우가있다. 로그파일의크기가커지는것은둘째치고서라도당장계속적으로커지는로그파일때문에서버에부하를유발하는것이더욱큰문제이다. 서버에서로그를남기는방식은매번클라이언트의요청이있을때마다웹서버에서패킷헤더에있는클라이언트의정보를받아낸후로그파일을 open 한후로그파일을읽어파일의제일끝으로이동하여로그정보를추가한후파일을 close 하는것인데, 불필요한요청이있을때마다이작업을계속하여야하
므로서버에부하를유발함은당연한현상이다. 따라서아예로그를남기지않도록하거나로그를남긴다하더라도불필요한정보를남기지않도록하는것이미소하게나마서버의성능을높이는것이될것이다. 그럼실제로불필요한정보는아예로그를남기지않는방법에대해알아보도록하자. 이를테면코드레드의경우아래와같이무차별적인로그가남게되는데 2001/08/01 23:39:50.765446 152.158.99.4:58781 -> 211.233.38.193:80 [AP] GET/default.ida?NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN 이러한로그를막기위해서는 httpd.conf 파일을열어 CustomLog 윗줄에 SetEnvIf Request_URI "/default.ida$" cord-red 와같이정의한후 CustomLog /usr/local/apache/logs/access.log combined 라고설정되어있는부분을 CustomLog /usr/local/apache/logs//access.log combined env=!cord-red 라고수정을한다.! 는 not 의의미이므로위설정은환경변수 cord-red 로정의된요청을거부하라는뜻이다. 위와같이설정후아파치를재시작하면코드레드와관련된로그가남지않게된다. 코드레드에이은 Nimda 웜의경우도같은방식으로설정하여로그에남지않도록설정할수있다. 또한같은원리를이용하여 iptables 를이용하여아예패킷자체를차단할수도있는데, 코드레드의경우 default.ida 문자열을요청한다는특징을이용하여 iptables A INPUT -i eth0 -p tcp --tcp-flags ACK ACK --dport 80 \ -m string --string '/default.ida?' -j REJECT --reject-with tcp-reset 와같이 iptables 의 strings 를이용하여특정문자열이포함된패킷을차단하는방법도있기는하지만이방법은커널과 iptables 를다시컴파일하여야하는문제가있다. Nimda Worm 역시이외 cmd.exe 와 root.exe 를포함하므로같은방식으로 iptables -A INPUT -p tcp --tcp-flags ACK ACK --dport 80 -m string --string "cmd.exe" -j REJECT -- reject-with tcp-reset iptables -A INPUT -p tcp --tcp-flags ACK ACK --dport 80 -m string --string "root.exe?" -j REJECT -- reject-with tcp-reset 와같이차단할수있다. 장애. ServerName 인자관련 아파치서버를시작시자주만나는에러와관련된설정중하나가바로아래와같은 ServerName 이다.
# /usr/local/apache/bin/apachectl start httpd: cannot determine local host name. Use the ServerName directive to set it manually../apachectl startl: httpd could not be started 대부분 ServerName 은리눅스설치시입력한호스트이름을자동으로가지고와설정되나 DNS 상에존재하지않은도메인명이나설사존재하더라도로컬서버가아닌잘못된도메인을정의시이러한현상이나타난다. 이러한경우에는 ServerName 을실제로컬서버의호스트이름이나 IP 주소로설정해주어야한다. 또한 ServerName 을잘못설정시나타날수있는현상중하나가 http://domain.com/~user 와같이접속할때의문제이다. 즉, 서버내계정사용자의홈페이지를접속시 http://domain.com/~user/ 와같이접속하면접속이되나 http://domain.com/~user 와같이 / 를붙이지않으면접속이되지않는경우이다. 클라이언트가서버의디렉토리에접속시끝에 / (trailing) 을하지않은경우서버는클라이언트에게 / 을붙여다시접속을하라고요청한다. 그렇지않으면상대 URL 경로를인식하지못하는문제가있기떄문이다. 만약 DNS 가정상적으로세팅되어작동하고있을경우에는문제가없지만그렇지않은경우에는접속이되지않는경우가생긴다. 또는위에서처럼 ServerName 에지정된호스트네임이실제로 DNS 상에리졸빙이되지않는경우도이러한현상이나타나므로이러한경우에는 httpd.conf 의 ServerName 옵션에실제서비스중인도메인명으로입력해주면된다. 장애. 특정파일의접근제한이되지않을때 가끔서버를운영하다보면특정한디렉토리이하에대해서는인증된유저만접속이가능하게한다거나특정 IP 대역의유저만접근하도록하고자할필요가있을때가있다. 특정디렉토리이하에대해서접근을제어하고자할때에는.htaccess 를사용하거나 httpd.conf 에서 <Directory> 를이용하여제어를할수있지만, 만약특정한파일에대해서외부에서의접근을제한하고자한다면어떻게하여야할까? 이때에는 Location 을사용하면된다. httpd.conf 파일에아래와같이설정시모든디렉토리이하의 secret.html 파일에대해서는 192.168.1.1 에서만접근이가능하게된다. <Location /secret.html> order deny,allow deny from all allow from 192.168.1.1 </Location>
만약여러도메인이설치되어있는호스팅서버의경우 secret.tt.co.kr 도메인내 secret.html 에 대해서만접근을제어하고자할경우에는아래와같이 VirtualHost 설정에서하면된다. <VirtualHost secret.tt.co.kr> ServerAdmin antihong@tt.co.kr DocumentRoot /usr/local/apache/htdocs/secret/ ServerName secret.tt.co.kr <Location /secret.html> order deny,allow deny from all allow from 192.168.1.1 </Location> </VirtualHost> 또는위와같이 IP 가아니라특정한 ID/PW 를입력한유저에대해서만특정파일에대하여 접근을허용하고자할때가있다. 이러한경우에는 httpd.conf 에아래와같이설정하면된다. <VirtualHost secret.tt.co.kr> ServerAdmin antihong@tt.co.kr DocumentRoot /usr/local/apache/htdocs/secret/ ServerName secret.tt.co.kr <Files secret.html> AuthName "ID/PW 를입력하세요." AuthType Basic AuthUserFile /usr/local/apache/htdocs/.htpasswd Require valid-user </Files> </VirtualHost> 그리고 htpasswd c.htpasswd id 로.htpasswd 파일에 ID/PW 를생성하여 secret.html 에접근 시 ID/PW 를정확히입력한유저에대해서만접근이가능하게된다. 장애. 한글도메인으로접속이되지않을때
한글.com 형식의한글도메인서비스가 1년가까이아직정상적인서비스가되고있지는않지만현재는포워딩방식으로나마일부사용가능하다. 즉, 그자체로한글.com 으로의사용은불가능하며단지한글.com 을접속시다른도메인으로포워딩할수있는것이다. 현재 http://www.gabia.com/ 나 http://www.doregi.com/ 등에서한글도메인을검색해보면예를들어팬메일.net 의경우 BQ--3DJSZOSUY56A.NET 와같이 BQ 형식의 RaceCode 문자로되어있는데, 실제로는 bq--3djszosuy56a.mltbd.net 와같이 mltbd.net( 한글.com 일경우에는 mltbd.com, 한글.org 일경우에는 mltbd.org ) 의 2차도메인형식으로서비스된다. 따라서위와같이 WHOIS 검색을한후나온 RaceCode 을 DNS 서버에서먼저설정하여야하는데, DNS 서버의 named.conf 에서설정하여야할내용은아래와같다. zone "bq--3djszosuy56a.mltbd.net" { type master; file "bq--3djszosuy56a.mltbd.net.zone"; }; bq--3djszosuy56a.mltbd.net.zone 파일의형식은일반 zone 파일형식과동일하게설정하면된다. 그리고 DNS 서버에서지정한해당웹서버에서는아래와같이 VirtualHost 설정을하여원래의사이트인 http://panmail.net/ 으로 Redirect 하면된다. ( 현재까지는포워딩서비스만제공하므로 Redirect 를이용하여야한다.) <VirtualHost bq--3djszosuy56a.mltbd.net> ServerAdmin webmaster@bq--3djszosuy56a.mltbd.net DocumentRoot /usr/local/apache/htdocs/panmail ServerName bq--3djszosuy56a.mltbd.net ServerAlias www.bq--3djszosuy56a.mltbd.net Redirect / http://panmail.net </VirtualHost> 위와같이설정후아파치를재시작하면팬메일.net 으로접속시 http://panmail.net/ 으로접속이되는것을확인할수있을것이다. 장애. 기타장애문제를해결하는방법
리눅스가윈도우계열과다른가장큰특징중하나는로그 (log) 를철저히남긴다는것이다. 남겨진로그정보를이용하여각종시스템의장애나상태를점검할수가있는데, 아파치웹서버역시마찬가지이다. 문제나장애가발생시에는반드시 error_log 를남기게하여 /usr/local/apache/logs/error_log 의메시지를살펴보면문제의원인과해결책을어렵지않게찾을수있게될것이다. 문제가발생하였다고당황하거나무턱대고관련게시판에질문을올리지말고, 에러로그의내용을기초로차근차근문제의원인을분석하고해결해나간다면조금씩조금씩서버관리자에가까워지는자신을발견할수있을것이다.