Apache(httpd)가 재시작되지 않을 때

  • 카카오톡 공유하기
  • 네이버 블로그 공유하기
  • 네이버 밴드에 공유하기
  • 페이스북 공유하기
  • 트위터 공유하기
  • 링크 복사하기

“서버 재시작했는데 왜 아파치가 안 뜨지?”

어느 날 갑자기 웹 서버가 응답하지 않습니다. 터미널에 익숙한 sudo systemctl start httpd 명령어를 입력하지만, 차가운 에러 메시지만이 나를 반깁니다.

Job for httpd.service failed because the control process exited with error code. See "systemctl status httpd.service" and "journalctl -xe" for details.

별거 아니겠지라고 생각했지만 이것이 길고 긴 디버깅 여정의 시작일 줄은 아무도 몰랐습니다.

이 서버는 연결된 다른 시스템들이 많기 때문에 빨리 실행을 띄우지 않으면 바로 연락이 올겁니다. 손에 땀이 나기 시작합니다. 그리고 설정을 변경하고 재시작을 해보면서 fail이 나면, 이것만한 롤러코스터가 없습니다.

실제로 겪었던 아파치(httpd) 서버 실행 실패 문제를 해결해 나가는 과정입니다.


1단계: 기본 점검, 그리고 첫 번째 함정 “Syntax OK”

모든 문제 해결의 시작은 로그 확인입니다. 시스템이 시키는 대로 journalctl -xe를 확인했지만, 보이는 것은 status=1/FAILURE라는 모호한 결과뿐. 구체적인 원인은 보이지 않습니다.

장애 대응 매뉴얼의 첫 번째 장을 펼칩니다. “설정 파일 문법을 확인하라.”

Bash

sudo httpd -t

터미널에 Syntax OK라는 반가운 메시지가 뜹니다. 오타는 아닙니다 하지만 안도감도 잠시, 서비스는 여전히 시작되지 않습니다. 이것이 바로 첫 번째 함정입니다. httpd -t는 문법만 검사할 뿐, 실행 환경의 문제를 알려주지는 않습니다.


2단계: 의심의 눈초리 – 포트, 권한, 그리고 SELinux

문법이 아니라면 실행 환경의 문제입니다. 원인을 좁혀봅니다.

  1. 포트 충돌? (sudo ss -tlpn | grep ':443')다른 서비스가 443 포트를 사용하고 있나? -> 아님.
  2. SELinux 보안 정책? (sudo setsebool -P httpd_can_network_connect 1)프록시 설정 때문에 SELinux가 막았나? -> 아님.
  3. SSL 인증서 파일 권한? (ls -l, sudo chown, sudo chmod)파일 소유권이나 권한이 잘못됐나? -> 수정했지만, 여전히 실패.
  4. SSL 인증서와 키가 짝이 맞나? (openssl x509 vs openssl rsa)해시값을 비교해보니… -> 완벽하게 일치함.

모든 이유를 찾아봤지만 문제는 여전히 미궁 속으로 빠져듭니다.


3단계: 마지막 단서, 아파치의 ‘비밀 일기장’을 열다

journalctl은 시스템의 공식적인 기록이지만, 정작 아파치 자신은 무슨 말을 하고 싶었을까요? 우리는 아파치가 직접 기록하는 자체 에러 로그(error_log)를 확인하기로 했습니다. 시스템 로그가 놓친 결정적인 단서가 그곳에 있었습니다.

Bash

sudo tail -n 50 /etc/httpd/logs/error_log

그리고 마침내, 결정적인 원인이 드러났습니다.

(28)No space left on device: AH00023: Couldn't create the ssl-cache mutex

“디바이스에 남은 공간이 없습니다.” 라는 메시지였습니다.


4단계: 진실 혹은 거짓 – “No space left on device”의 두 얼굴

드디어 원인을 찾았다는 기쁨도 잠시, 혼란이 찾아옵니다.

Bash

df -h

디스크 공간을 확인하니 모든 파티션이 8%, 6%… 넉넉하기만 합니다. 어떻게 된 일일까요?

“No space left on device”는 우리를 속이기 위한 범인의 트릭이었습니다. 이 메시지는 두 가지 의미를 가집니다.

  1. 정말 디스크 공간이 부족한 경우 (이번엔 아님)
  2. 시스템 IPC 리소스, 즉 세마포어(Semaphore)가 고갈된 경우

아파치는 SSL 세션이나 프록시 연결을 관리하기 위해 ‘세마포어’라는 시스템 자원을 사용합니다. 하지만 아파치가 비정상적으로 반복해서 종료되면, 미처 정리되지 못한 ‘유령 세마포어’들이 시스템에 계속 쌓이게 됩니다. 결국, 시스템이 할당할 수 있는 세마포어 개수 한도를 초과해버린 것입니다.

원인은 바로 “고갈된 세마포어 리소스” 였습니다!

세마포어는 비교하자면, n개의 칸을 보유한 화장실의 문지기 입니다. 빈칸이 있을 때 들어가도록 허용해주는 문지기가 공간이 비워지면 요청자를 들여보내는 역할을 합니다. 오랜 시간 비정상적으로 종료되서 화장실에 들어가서 안나온 아이(?)들을 한번에 내몰아서 깨끗하게 정리하는 과정이라고 보시면 됩니다.

에러 로그 중에 mutex 라는 것도 있는데요. 이것은 화장실 한칸에 사람이 있다 없다만 알려주는 개념입니다. 단일 리소스에 대한 통제를 mutex에서 여러 리소스에 대한 동시 통제를 semaphore에 한다고 생각하면 됩니다.


최종 해결: 유령들을 청소하라

원인을 알았으니 해결은 간단합니다. 아파치 소유의 모든 유령 세마포어를 한 번에 정리합니다.

Bash

# 'apache' 유저가 소유한 모든 세마포어를 찾아서 한 번에 삭제
ipcs -s | grep apache | awk '{print $2}' | xargs -I {} sudo ipcrm -s {}

그리고 마침내…

Bash

sudo systemctl start httpd

아무런 에러 메시지 없이, 아파치는 조용히 기동을 시작했습니다. 길고 길었던 장애 추적이 끝나는 순간이었습니다.


## 이 여정의 교훈

이번 장애 추적을 통해 우리는 몇 가지 중요한 교훈을 얻었습니다.

  1. 시스템 로그(journalctl)가 전부가 아니다. 때로는 애플리케이션 자체의 로그(error_log)에 결정적인 단서가 있다.
  2. Syntax OK는 시작일 뿐이다. 문법이 아닌 실행 환경의 문제를 항상 염두에 두어야 한다.
  3. 에러 메시지의 숨은 의미를 파악하라. No space left on device가 항상 디스크 공간을 의미하는 것은 아니다.
  4. 포기하지 말고, 체계적으로 접근하라. 하나씩 가능성을 제거해나가는 것이 문제 해결의 왕도다.

이 글이 언젠가 비슷한 문제로 밤을 지새울 다른 개발자에게 작은 등불이 되기를 바랍니다. Happy Debugging!

댓글

답글 남기기

이메일 주소는 공개되지 않습니다. 필수 필드는 *로 표시됩니다