📚 네트워크 · 패킷 분석 › 05. 네트워크 스캔 징후 분석 — 211편
이전 글: 210. Port Range Scan · 다음 글: 212. OS Detection
Service Detection(서비스 탐지) 은 포트 스캔으로 찾은 열린 포트에 실제로 어떤 프로토콜의 서비스가 동작하는지 응답 내용으로 확인하는 단계입니다. 포트 스캔 결과의 서비스 이름은 "22번이면 SSH"처럼 포트 번호로 추정한 값일 뿐이므로(204. Nmap 기본 사용법), 상대는 연결을 맺고 서버가 보내는 데이터를 보고 판단합니다.
관제자 입장에서 이 단계는 포트 스캔보다 한 걸음 더 들어온 신호입니다. 연결이 완성되고 데이터가 오가므로 서비스 로그에도 흔적이 남습니다. 제품명과 버전까지 확인하는 과정은 213. Version Detection에서 따로 다룹니다.
| 구분 | 포트 번호 기반 추정 | 응답 기반 서비스 탐지 |
|---|---|---|
| 판단 근거 | 포트 번호와 서비스 이름 대응표 | 서버가 보낸 배너·응답 형식 |
| 연결 수립 | 필요 없음 | 필요함(Handshake 완료) |
| 비표준 포트 서비스 | 잘못 판단 | 실제 프로토콜 식별 |
| 서비스 로그 흔적 | 거의 없음 | 연결·오류 기록이 남음 |
서비스는 연결 직후 누가 먼저 데이터를 보내는지에 따라 두 부류로 나뉩니다. 서비스 탐지는 먼저 서버가 말하기를 기다리고, 응답이 없으면 여러 프로토콜 형식의 요청을 보내 반응을 비교합니다.
열린 포트 목록 (포트 스캔 결과)
↓
TCP 연결 완료 (SYN → SYN/ACK → ACK)
↓
몇 초간 대기 ── 서버가 먼저 배너 전송? ── 예 → 배너 형식으로 서비스 판단
│
아니오
↓
프로토콜 형식 요청 전송 (HTTP 요청, TLS 시작, 빈 줄 등)
↓
응답을 서명 DB와 비교 → 일치하면 판단, 아니면 다음 요청(새 연결)
↓
방어 측 흔적: 허용 세션 여러 개 / 서비스 로그 오류 / 요청 데이터가 짧고 형식이 제각각
| 부류 | 대표 서비스 | 서버의 첫 응답 예 | 방어 측에서 보이는 것 |
|---|---|---|---|
| 서버 선발화 | SSH, FTP, SMTP, POP3 | SSH-2.0-..., 220 ..., +OK | 배너만 받고 끊긴 짧은 세션 |
| 클라이언트 선발화 | HTTP, TLS, RDP, SMB | 요청이 와야 응답 | 형식이 다른 요청이 같은 포트로 여러 번 |
| 기준 | 정상 클라이언트 | 서비스 탐지 |
|---|---|---|
| 포트당 세션 수 | 업무 흐름에 따라 | 짧은 시간 여러 개 |
| 요청 내용 | 그 서비스 형식에 맞음 | 형식이 제각각, 최소 요청 |
| 인증·업무 요청 | 이어짐 | 없음 |
| 서비스 로그 | 정상 처리 | 400·408, preauth 종료 같은 오류 |
실습 예시 — 본인 소유 실습망에서 서비스 탐지 흔적을 확인하는 방어 측 명령입니다. 값은 환경마다 다릅니다.
# SSH 로그: Rocky는 /var/log/secure, Ubuntu는 /var/log/auth.log
sudo grep -E 'sshd.*(preauth|identification|banner exchange)' /var/log/secure | tail
# 웹 접근 로그: Rocky는 /var/log/httpd/access_log, Ubuntu는 /var/log/apache2/access.log
sudo awk '$9 ~ /^(400|408)$/ {print $1}' /var/log/apache2/access.log | sort | uniq -c | sort -rn
# Zeek conn.log: 목적지 포트와 Zeek가 식별한 프로토콜(service) 비교
zeek-cut id.orig_h id.resp_p service conn_state orig_bytes resp_bytes < conn.log
서비스 로그 형식 예시(값은 환경마다 다름, OpenSSH·Apache 버전에 따라 문구가 다름):
sshd[2231]: Connection closed by 203.0.113.45 port 50412 [preauth]
sshd[2240]: banner exchange: Connection from 203.0.113.45 port 50420: invalid format
203.0.113.45 - - [30/Sep/2026:10:02:11 +0900] "GET / HTTP/1.0" 200 612
203.0.113.45 - - [30/Sep/2026:10:02:12 +0900] "\x16\x03\x01..." 400 226
203.0.113.45 - - [30/Sep/2026:10:02:18 +0900] "-" 408 -
| 관찰 | 해석 |
|---|---|
| sshd에 인증 시도 없이 preauth 종료 | 배너만 받고 끊음 → SSH 존재 확인 |
| SSH 포트에 형식 오류(invalid format) | SSH가 아닌 요청이 도착 → 여러 형식 시험 |
웹 로그에 \x16\x03 로 시작하는 400 | 평문 HTTP 포트에 TLS 시작 데이터 전송 |
| 요청 없는 408 | 서버가 먼저 말하는지 기다린 연결 |
| Zeek service가 포트와 다름 | 예: 8443에서 ssh 식별 → 비표준 포트 서비스 노출 |
| 흔적 위치 | 확인 내용 |
|---|---|
| 방화벽 세션 로그 | 열린 포트에 대한 허용 세션 반복, 바이트 소량 |
| 서비스 로그 | preauth 종료, 400·408, 형식 오류 |
| Zeek·NDR | service 필드와 포트 불일치, 짧은 세션 |
| IDS | 스캔 도구 특징 요청 관련 Alert(룰셋에 따라 다름) |
관제자가 확인할 질문
오탐 주의: 로드밸런서·모니터링 시스템의 헬스체크도 요청 한 번 후 끊기는 짧은 세션을 만듭니다. 헬스체크는 출발지와 요청 경로가 고정되고 일정 주기로 반복된다는 점이 다릅니다. 자산관리 솔루션의 서비스 식별도 예외 목록과 대조합니다.
service 필드와 목적지 포트가 다르면 비표준 포트 서비스 노출을 의심합니다.