13.3.2.1. NTRIP(v1/v2) 프로토콜(HTTP/TCP 기반) 헤더 구조 및 Base64 인증(Authentication) 인코딩 메커니즘

13.3.2.1. NTRIP(v1/v2) 프로토콜(HTTP/TCP 기반) 헤더 구조 및 Base64 인증(Authentication) 인코딩 메커니즘

무인 항공기(UAS)의 지상 관제국(GCS)인 QGroundControl이 캐스터(Caster) 서버로부터 RTCM 보정 데이터를 끌어오기 위해서는, 전 세계 표준으로 자리 잡은 NTRIP(Networked Transport of RTCM via Internet Protocol) 규격을 준수하여 통신을 개시해야 한다. 이름에서 알 수 있듯 NTRIP은 완전히 새로운 외계의 통신 방식이 아니라, 우리가 매일 웹 브라우징에 사용하는 익숙한 HTTP/TCP 소켓(Socket) 뼈대 위에 측위 데이터를 얹어 나르는 프로토콜이다.

본 절에서는 QGC의 백엔드 C++ 클라이언트가 캐스터 서버에 최초로 TCP 연결을 맺고, 마운트포인트(Mountpoint)를 요청하며, 어떻게 자신의 신분을 증명(Authentication)하여 바이너리 스트림의 수문을 여는지 그 HTTP 기반 헤더 레벨의 트랜잭션을 상세히 분석한다.

1. NTRIP 버전별 프로토콜 기반 지식 (v1 vs v2)

NTRIP 클라이언트(QGC)와 서버(캐스터) 간의 관계는 웹 브라우저와 웹 서버(Apache, Nginx 등)의 관계와 거의 동일하다.

  • NTRIP v1.0: 순수하게 오디오 인터넷 스트리밍 프로토콜인 Icecast / SHOUTcast 기술을 GPS 데이터 전송용으로 차용한 아키텍처이다. HTTP의 형태를 띠고 있으나, 표준 HTTP/1.1 규격을 완벽히 따르지 않는 야매성(Ad-hoc) 통신(예: 본문 길이 Content-Length 지정 없이 무한 스트리밍 개시)을 수행하기 때문에 특정 방화벽이나 프록시(Proxy)에서 필터링당하는 약점이 있다.
  • NTRIP v2.0: 이러한 약점을 보완하여 완벽한 HTTP/1.1 표준 규격으로 재작성된 버전이다. Transfer-Encoding: chunked 같은 진보된 HTTP 청크 전송 방식을 차용하여 라우터의 심층 패킷 검사(DPI)를 무사히 통과하며, 양방향 통신(클라이언트가 NMEA를 서버로 올리는 행위)을 더욱 명확하게 규정한다.

현대의 QGC 통신 엔진은 캐스터가 지원한다면 NTRIP v2.0 협상을 우선적으로 시도한다.

2. TCP 소켓 연결 및 GET 요청 헤더(Header) 구조

사용자가 QGC의 ‘RTK GPS’ 설정 창에서 캐스터 주소(Host IP), 포트(주로 2101), 마운트포인트 명칭, 그리고 계정 정보를 입력하고 Connect 버튼을 누르면, 백엔드의 소켓 스레드가 서버와 3-way Handshake를 맺고 다음과 같은 ASCII 텍스트 기반의 HTTP GET 리퀘스트를 날린다.

GET /VRS-RTCM31 HTTP/1.1
Host: ntrip.gnss.go.kr:2101
Ntrip-Version: Ntrip/2.0
User-Agent: QGroundControl/4.3.0
Authorization: Basic YWRtaW46cGFzc3dvcmQxMjM=
Connection: close

2.1 Request Line (요청 라인) 파싱

  • GET /VRS-RTCM31 HTTP/1.1: 루트 디렉토리(/) 뒤에 붙는 경로명 VRS-RTCM31 이 바로 마운트포인트(Mountpoint) 이다. 캐스터 서버는 이 위치 정보를 보고 “아, 이 드론은 L1/L2 듀얼밴드용 RTCM 3.1 규격의 가상 참조국 데이터를 원하고 있구나” 라고 판단하여 해당 큐(Queue)의 파이프를 클라이언트 소켓과 연결해 준다.

2.2 User-Agent 및 메타데이터

  • Ntrip-Version: 클라이언트가 수용할 수 있는 프로토콜 레벨을 명시한다.
  • User-Agent: 단순 웹로봇 공격과 구별하기 위해 클라이언트 명칭을 삽입한다. 국토지리정보원 같은 공공 캐스터는 알 수 없는 User-Agent의 대량 접속을 차단(Ban)하기도 하므로 C++ 단에서 명확한 앱 서명을 기입해야 한다.

3. Base64 기반의 Basic Authentication 메커니즘

대부분의 상용/공공 NTRIP 캐스터 서비스는 대역폭 보호를 위해 익명(Anonymous) 접속을 불허한다. 따라서 클라이언트는 자신이 인가받은 사용자임을 증명해야 하는데, NTRIP 프로토콜은 웹 통신의 전통적인 HTTP Basic Authentication 방식을 그대로 따른다.

3.1 인증 문자열의 인코딩 절차

QGC 사용자가 UI 화면의 텍스트 필드에 아이디(admin)와 비밀번호(password123)를 치면, C++ 해시 로직은 이를 평문(Plain/Text) 그대로 전송하지 않는다.

  1. 조합(Concatenation): 양 문자열 사이에 콜론(:) 문자를 끼워 넣어 하나의 문자열로 합친다. (결과: admin:password123)
  2. Base64 인코딩(Encoding): 이 아스키코드 바이트 배열을 6비트씩 잘라서 알파벳 및 숫자로 치환하는 Base64 인코딩 함수를 통과시킨다. (결과: YWRtaW46cGFzc3dvcmQxMjM=)
  3. 헤더 삽입: 인코딩된 결과물 앞에 Basic 이라는 키워드를 붙여 Authorization 헤더 필드에 밀어 넣는다.

3.2 보안적 한계점과 대응 사상

엔지니어라면 여기서 중대한 보안 취약점을 간파해야 한다. Base64는 암호화(Encryption)가 아닌 단순 치환 인코딩(Encoding)이기 때문에, 해커가 중간에서 Wireshark로 패킷을 탈취(Sniffing)하여 디코더에 집어넣으면 1\text{초} 만에 원래의 ID와 비밀번호가 평문으로 노출된다.

그럼에도 드론 업계에서 NTRIP이 여전히 이 허술한 방식을 쓰는 이유는 장비(특히 10년 넘은 측량기나 소형 임베디드 모뎀)의 연산성(Computing Power) 극복 및 표준 소급성 때문이다. TLS/SSL 위증명서 기반의 ‘NTRIPs (Secure)’ 규격이 서서히 태동하고 있긴 하나, 아직 대부분의 공용 Caster 망은 평문 TCP 2101 포트를 기본값으로 열어둔다.

4. 응답(Response)과 바이너리 스트리밍(Streaming)의 전환

캐스터 서버가 인증 헤더의 Base64를 풀어서 유효한 계정임을 확인하면, 다음과 같은 성공 응답을 내린다. (NTRIP v2 기준)

HTTP/1.1 200 OK
Ntrip-Version: Ntrip/2.0
Server: NTRIP Caster/2.0.xyz
Date: Wed, 16 Aug 2026 13:45:00 GMT
Content-Type: gnss/data
Transfer-Encoding: chunked

200 OK 헤더 덩어리 직후, 두 번의 줄바꿈 개행문자(\r\n\r\n)를 끝표시로 하여 텍스트 기반의 HTTP 협상은 완전히 종료된다.
이 바로 다음 바이트부터 소켓의 성질이 완전히 바뀐다. 더 이상의 텍스트 문자열은 없고, 0xD3 헥스(Hex) 값으로 시작하는 알 수 없는 검은색 바이너리 덩어리(RTCM Message)들이 영원토록 쏟아져 내리기 시작한다.

QGC 클라이언트의 소켓 수신 스레드는 개행 문자 탐지 직후, 파서(Parser)의 모드를 ’문자열 파서’에서 ’바이나리 구조체 디코더’로 스위칭(Context Switching)하며, 이 묵직한 데이터 패킷들을 앞서 배웠던 MAVLink GPS_RTCM_DATA 래퍼(Wrapper)로 밀어 넣기 위한 가열찬 컨베이어 벨트를 돌리기 시작하는 것이다.