레거시 산업제어시스템(ICS) 프로토콜 다수는 인증이 없다. 명령을 보낸 주체가 누구인지 검증하지 않고, 메시지가 도중에 변조됐는지도 확인하지 않으며, 접근 통제를 서버(현장 장치)가 아니라 클라이언트(엔지니어링 도구)에 맡긴다. 이것을 두고 "설계자가 보안을 몰랐다"고 말하는 것은 게으른 진단이다. 실제로는 당대의 제약 조건에서 합리적이었던 선택이 20년의 네트워크 연결성 증가와 만나 부채로 전환된 것이다.
이 글은 특정 벤더 프로토콜을 분석하지 않는다. 대신 Modbus, DNP3 같은 공개된 레거시 프로토콜을 예로 들어, 레거시 ICS 프로토콜이 공유하는 네 가지 구조적 결함 — 인증 부재, 단순 합산 체크섬, 클라이언트 측 접근 통제, 인증 없는 시각/설정 쓰기 — 이 각각 어떤 설계 논리에서 나왔고 왜 지금은 위험한지를 다룬다.
왜 인증이 없었는가: 폐쇄망이라는 전제
1970~2000년대에 설계된 산업 프로토콜의 위협 모델은 오늘날의 그것과 근본적으로 달랐다. 당시 전제는 세 가지였다.
첫째, 물리적 격리. 제어 네트워크는 공장 담장 안에 있었고, 시리얼 케이블이나 전용 필드버스로 물리적으로 분리돼 있었다. 통신 링크에 접근하려면 그 케이블에 물리적으로 손을 대야 했다. 물리 접근이 곧 인증이었다. 담장 안에 들어온 사람은 이미 신뢰된 사람이라는 가정이다.
둘째, 결정론과 지연 예산. 산업 제어는 실시간이다. PLC 스캔 주기는 밀리초 단위이고, 안전 계장(SIS)의 응답 시한은 더 빡빡하다. 1990년대의 임베디드 CPU — 수 MHz 클럭, 수십 KB RAM — 에서 매 메시지마다 암호 서명을 계산하고 검증하는 것은 지연 예산과 연산 예산 양쪽에서 감당할 수 없었다. HMAC 한 번이 스캔 주기를 넘기면 제어 루프가 깨진다.
셋째, 상호운용성과 수명. 산업 장비의 설계 수명은 15~30년이다. 프로토콜은 여러 벤더의 장비가 섞인 환경에서 수십 년 동안 호환돼야 했다. 단순한 프로토콜일수록 구현 오류가 적고 상호운용이 쉽다. 복잡한 암호 협상 계층은 상호운용성의 적이었다.
이 세 전제 아래에서 "인증 없음"은 결함이 아니라 최적화였다. 문제는 전제가 무너졌다는 것이다. IT/OT 융합, 원격 유지보수, 클라우드 SCADA, 스마트 팩토리가 물리적 격리를 걷어냈다. 위협 모델의 전제는 사라졌는데 프로토콜의 설계 결정은 그대로 남았다. 부채란 원래 그렇게 생긴다 — 상환 시점이 아니라 조건이 바뀌었을 때 청구서가 온다.
Modbus: 교과서적 사례
가장 널리 쓰이는 산업 프로토콜인 Modbus(1979년 Modicon 발표)는 이 유산의 표본이다. Modbus의 요청 프레임은 대략 이렇게 생겼다.
[유닛 주소] [함수 코드] [데이터] [체크섬]여기 어디에도 "누가 이 명령을 보냈는가"를 나타내는 필드가 없다. 함수 코드 0x06(단일 레지스터 쓰기)이나 0x05(단일 코일 쓰기)를 담은 프레임은, 그것이 정당한 엔지니어링 워크스테이션에서 왔든 네트워크에 침투한 공격자의 노트북에서 왔든 완전히 동일하게 처리된다. 서버(슬레이브)는 발신자를 구분할 방법이 없다. Modbus/TCP(502 포트)로 넘어오면서 시리얼의 물리적 격리마저 사라졌지만, 프레임 구조는 1979년 그대로다.
이것이 레거시 ICS 프로토콜의 첫 번째 공통 결함이다: 메시지 단위 인증의 완전한 부재. 세션을 여는 시점에 비밀번호를 한 번 확인하는 프로토콜조차, 세션이 열린 뒤 개별 명령에는 인증 토큰을 붙이지 않는 경우가 많다. 그렇다면 세션 하이재킹이나 단순 패킷 재전송(replay)만으로 임의 명령을 주입할 수 있다.
단순 합산 체크섬: 오류 검출과 위변조 방지의 혼동
레거시 프로토콜의 두 번째 공통 결함은 무결성 메커니즘의 성격을 오해하게 만든다. 많은 레거시 프로토콜이 프레임 끝에 체크섬을 붙인다. 문제는 그 체크섬이 대개 바이트 단순 합산(sum-of-bytes)이나 LRC/CRC 같은 오류 검출 코드라는 점이다.
여기서 반드시 구분해야 할 것이 있다.
| 목적 | 메커니즘 | 방어 대상 |
|---|---|---|
| 오류 검출 (error detection) | 합산 체크섬, LRC, CRC | 전송 중 우발적 비트 반전 (전기 노이즈, 케이블 결함) |
| 무결성 보증 (integrity) | HMAC, 디지털 서명 | 의도적 변조 (공격자의 재작성) |
바이트 합산 체크섬은 오류 검출용이다. 열악한 시리얼 라인에서 노이즈로 뒤집힌 비트를 잡아내려고 설계됐다. 이것은 그 목적에는 충분하다. 하지만 공격자에 대한 방어는 전혀 되지 않는다. 공격자가 페이로드를 원하는 대로 바꾼 다음, 바뀐 페이로드에 맞는 체크섬을 다시 계산해서 붙이면 그만이다. 체크섬 계산 규칙은 공개돼 있고 연산은 자명하다. CRC도 마찬가지다 — CRC는 키가 없는 공개 함수이므로, 페이로드를 고치고 CRC를 재계산하는 것을 막지 못한다.
즉 "체크섬이 있으니 무결성이 보장된다"는 것은 범주 오류다. 오류 검출 코드와 메시지 인증 코드(MAC)는 이름이 비슷하고 프레임에서 같은 위치를 차지하지만 위협 모델이 정반대다. 전자는 자연을, 후자는 적을 상대한다. 레거시 프로토콜의 프레임을 감사할 때 이 둘을 혼동하면 "무결성 보호가 있다"는 잘못된 안심에 빠진다.
DNP3(전력·수도 SCADA에서 널리 쓰이는 프로토콜)의 원본 사양도 오랫동안 이 상태였다. DNP3는 링크 계층에 CRC를 두지만 그것은 순수 오류 검출이었고, 명령의 진위를 보증하지는 못했다. 이 공백을 메우기 위해 나중에 DNP3 Secure Authentication(SA, IEEE 1815 기준) 이 별도로 추가됐다는 사실 자체가, 원 프로토콜에 인증이 없었음을 반증한다. 무결성은 사후에 볼트온(bolt-on)으로 붙일 수 있지만, 그렇게 붙인 계층은 하위 호환성 협상 구간에서 다운그레이드 공격에 노출되기 쉽다.
클라이언트 측 접근 통제: 신뢰의 위치가 틀렸다
세 번째 결함은 가장 미묘하고, 그래서 가장 위험하다. 많은 레거시 프로토콜에서 접근 통제 규칙을 강제하는 주체가 서버(현장 장치)가 아니라 클라이언트(엔지니어링 소프트웨어)다.
전형적인 패턴은 이렇다. 프로토콜 사양에 "특정 메모리 영역은 읽기 전용", "이 영역은 쓰기 금지"라는 규칙이 있다. 그런데 그 규칙을 엔지니어링 도구가 UI/소프트웨어 레벨에서 막는다. 사용자가 도구에서 읽기 전용 영역에 쓰려고 하면 도구가 거부한다. 정작 현장 장치의 펌웨어는 그 쓰기 요청이 오면 그대로 수행한다. 장치는 "정상적인 도구라면 애초에 이런 요청을 보내지 않을 것"이라고 가정하고 클라이언트를 신뢰한다.
이것은 보안 원칙의 정면 위반이다. 신뢰 경계(trust boundary)의 반대편에 있는 것을 신뢰해서는 안 된다. 접근 통제는 자원을 소유한 쪽 — 서버 — 에서 강제돼야 한다. 클라이언트 측 검증은 편의 기능일 뿐 보안 기능이 아니다. 공격자는 벤더의 엔지니어링 도구를 쓸 의무가 없다. 프로토콜 사양을 읽고 프레임을 직접 조립하는 스크립트를 짜면, 클라이언트가 강제하던 모든 규칙 — 읽기 전용 영역, 쓰기 금지 구간, 위험 명령 차단 — 을 그냥 통과한다.
웹 보안에 익숙한 독자라면 이것이 클라이언트 측 유효성 검사만 믿는 웹 폼과 똑같은 실수임을 알 것이다. JavaScript로 입력을 검증하지만 서버에서는 검증하지 않는 API는, curl 한 줄로 우회된다. ICS에서도 원리는 동일하다. 다른 점은 결과의 무게다. 웹에서는 데이터 무결성이 깨지지만, OT에서는 물리 프로세스가 통제를 벗어난다.
이 결함이 특히 나쁜 이유는 감사할 때 잘 안 보인다는 것이다. 벤더 도구로 시스템을 다뤄 본 엔지니어는 "읽기 전용 영역은 못 건드린다"고 경험적으로 믿는다. 실제로 도구를 통해서는 못 건드리기 때문이다. 그 보호가 클라이언트에만 존재한다는 사실은, 프로토콜을 직접 구현해 프레임을 보내 보기 전에는 드러나지 않는다.
인증 없는 RTC/설정 쓰기: 로그 위변조로 가는 길
네 번째 결함은 앞의 세 가지가 합쳐진 곳에서 특히 날카로워진다. 많은 레거시 장치는 실시간 시계(RTC)와 시스템 설정을, 인증 없이, 일반 메모리 쓰기 명령으로 변경할 수 있게 한다.
RTC 쓰기가 왜 보안 문제인지는 얼핏 와닿지 않는다. 시계를 맞추는 것이 뭐가 위험한가? 문제는 RTC가 감사 로그와 이벤트 타임스탬프의 근원이라는 데 있다. 장치가 남기는 모든 이벤트 — 명령 수신, 모드 전환, 알람 발생, 안전 트립 — 는 RTC의 시각으로 찍힌다.
공격자가 인증 없이 RTC를 조작할 수 있으면 다음이 가능해진다.
- 로그 순서 교란. 시계를 되감았다 앞당겼다 하면 이벤트의 시간 순서가 뒤엉킨다. 사고 조사 시 "무슨 일이 어떤 순서로 일어났는가"를 재구성할 수 없게 된다.
- 알리바이 조작. 공격 행위 직전에 시계를 미래로 보내 두면, 실제 공격 이벤트의 타임스탬프가 정상 운영 시간대 밖으로 밀려나 정상 로그 검토에서 누락된다.
- 상관 분석 무력화. SIEM/SOC는 여러 장치의 로그를 타임스탬프로 상관시켜 공격 체인을 재구성한다. 한 장치의 시계가 조작되면 그 상관 관계가 깨진다.
즉 인증 없는 RTC 쓰기는 감사 추적(audit trail)의 신뢰성을 근본에서 무너뜨린다. 그리고 감사 로그는 사고 대응·포렌식·규제 준수의 마지막 보루다. 이 보루가 인증 없는 한 줄의 쓰기 명령으로 위변조될 수 있다면, 사고 후에 "실제로 무슨 일이 있었는가"를 입증할 방법이 사라진다.
설정 영역도 마찬가지다. 통신 파라미터, 알람 임계값, 보호 로직 설정을 인증 없이 바꿀 수 있으면, 공격자는 보호 계전기의 임계값을 무력화하거나 알람을 침묵시킨 뒤 파괴적 명령을 실행하고, 흔적을 지울 수 있다.
여기서도 핵심은 에러 코드 체계에 보안 개념이 아예 없다는 점에서 드러난다. 레거시 프로토콜의 NAK/에러 응답 카탈로그를 보면 "잘못된 주소", "지원하지 않는 명령", "모드 불일치" 같은 기능적 오류는 정교하게 분류돼 있지만, "인증 실패"나 "권한 부족" 같은 보안 오류 코드는 존재하지 않는다. 프로토콜에 인증 실패라는 개념 자체가 없다는 것은, 설계 시점에 인증이라는 개념이 아예 위협 모델에 없었다는 가장 직접적인 증거다.
부채를 상환하기: 무엇을, 어디서 고쳐야 하는가
이 네 가지 결함은 서로 얽혀 하나의 시스템적 부채를 이룬다. 정리하면 이렇다.
| 결함 | 당대의 합리성 | 오늘의 위험 | 상환 방향 |
|---|---|---|---|
| 메시지 인증 부재 | 폐쇄망 전제, 연산 예산 | 임의 명령 주입, 재전송 공격 | 세션·메시지 인증(예: DNP3-SA), 게이트웨이 |
| 단순 합산/CRC 체크섬 | 시리얼 노이즈 검출 | 페이로드 위변조 무방비 | MAC/서명, TLS 래핑 |
| 클라이언트 측 접근 통제 | 상호운용성, 단순 펌웨어 | 도구 우회로 규칙 전면 무력화 | 서버 측 강제, 프로토콜 인지 방화벽 |
| 인증 없는 RTC/설정 쓰기 | 편의성 | 로그 위변조, 포렌식 무력화 | 시각 동기 인증(NTP/PTP 인증), 쓰기 인가 |
여기서 게으른 선임 개발자의 관점 하나를 덧붙이고 싶다. 이 부채의 상당 부분은 프로토콜 자체를 뜯어고쳐서 갚는 것이 아니다. 15~30년 수명의 현장 장치 펌웨어를 전부 교체하는 것은 대개 비현실적이고, 그렇게 하려다 안전 인증을 다시 받아야 하는 등 더 큰 위험을 부른다. 현실적인 상환은 경계에서 이루어진다.
- 분리(segmentation) — 물리적 격리라는 원래 전제를 네트워크 세그멘테이션과 데이터 다이오드로 복원한다. 프로토콜의 위협 모델이 상정했던 조건을 다시 만들어 주는 것이다. 이것이 가장 저렴하고 확실한 상환이다.
- 프로토콜 인지 게이트웨이/방화벽 — 서버가 강제하지 못하는 접근 통제를, 경계의 게이트웨이가 대신 강제한다. "이 소스에서 이 함수 코드로 이 영역에 쓰는 것"을 화이트리스트로 통제한다.
- 인증 래핑 — 프로토콜 자체를 못 바꾸면, TLS 터널이나 인증 게이트웨이로 감싼다. DNP3-SA처럼 표준화된 인증 확장이 있으면 그것을 켠다.
- 모니터링과 시각 무결성 — 인증 없는 RTC 쓰기를 완전히 막지 못하더라도, 최소한 그 명령을 탐지하고 별도의 신뢰 가능한 시각원(인증된 NTP/PTP)으로 로그 타임스탬프를 이중화한다.
가장 중요한 교훈은 진단의 태도에 있다. 레거시 ICS 프로토콜의 보안 결함을 볼 때 "설계자가 무능했다"고 결론짓는 것은 틀렸을 뿐 아니라 위험하다. 틀린 이유는 그것이 사실이 아니기 때문이고, 위험한 이유는 그 진단이 "똑똑한 우리가 다시 설계하면 된다" 는 오만으로 이어지기 때문이다. 실제 교훈은 반대다: 오늘 우리가 "폐쇄망이니까", "성능 예산이 없으니까", "우리 클라이언트만 접근하니까"라고 정당화하며 내리는 설계 결정이, 20년 뒤 누군가에게 정확히 같은 종류의 청구서로 돌아온다는 것. 위협 모델의 전제는 언젠가 무너진다. 부채는 그때 청구된다. 레거시 ICS 프로토콜은 그 청구서를 지금 우리에게 보여 주고 있는, 살아 있는 사례 연구다.
