TL;DR
- TLS = 인터넷 보안의 기반: HTTPS, gRPC, 모든 보안 통신
- TLS 1.3 (2018): 1-RTT 핸드셰이크, 약한 암호 제거, 0-RTT 지원
- Forward Secrecy: ECDHE로 과거 통신 보호
- 인증서 체인: Leaf → Intermediate → Root CA
- mTLS: 양방향 인증, Zero-trust 아키텍처의 핵심
- Post-Quantum: NIST 표준화, 양자 컴퓨팅 시대 대비
1. TLS의 진화
1.1 SSL → TLS 역사
| 버전 | 연도 | 상태 |
|---|---|---|
| SSL 1.0 | 1994 | 출시 안 됨 |
| SSL 2.0 | 1995 | 폐기 (취약) |
| SSL 3.0 | 1996 | 폐기 (POODLE 공격) |
| TLS 1.0 | 1999 | 폐기 (BEAST) |
| TLS 1.1 | 2006 | 폐기 (낮은 보안) |
| TLS 1.2 | 2008 | 사용 가능 (구식) |
| TLS 1.3 | 2018 | 권장 |
2025년 현재: TLS 1.2와 1.3만 사용. SSL은 죽음.
1.2 왜 TLS인가?
HTTP의 문제:
- 평문 전송 → 도청 가능
- 무결성 보장 X → 변조 가능
- 신원 확인 X → 가짜 서버
TLS의 해결:
- 암호화 → 도청 방지
- 무결성 → MAC/HMAC
- 인증 → 인증서
1.3 TLS의 위치
Application Layer [HTTP, gRPC, ...]
↓
TLS [Encryption, Auth]
↓
Transport Layer [TCP, QUIC]
↓
Network Layer [IP]
위치: 애플리케이션과 전송 계층 사이.
2. 암호학 기초
2.1 대칭 vs 비대칭
대칭 암호화:
- 같은 키로 암호화/복호화
- 빠름
- 키 공유가 문제
- 예: AES, ChaCha20
비대칭 암호화:
- 공개 키 (암호화) + 개인 키 (복호화)
- 느림
- 키 공유 안전
- 예: RSA, ECDSA
TLS는 둘 다 사용:
- 비대칭으로 키 협상
- 대칭으로 데이터 암호화
2.2 해시 함수
SHA-256("Hello") = "185f8db32271fe25..."
특성:
- 일방향 (역산 불가)
- 충돌 저항 (다른 입력 → 같은 출력 X)
- 빠름
용도:
- 비밀번호 저장 (bcrypt, Argon2)
- 무결성 검증
- 디지털 서명
2.3 디지털 서명
서명 = encrypt_with_private_key(hash(message))
검증:
expected_hash = decrypt_with_public_key(signature)
actual_hash = hash(message)
if expected_hash == actual_hash: 진짜
효과: 메시지 무결성 + 발신자 인증.
2.4 Diffie-Hellman 키 교환
문제: 두 사람이 안전하지 않은 채널에서 비밀 키를 공유?
Diffie-Hellman:
- 공개 매개변수 (p, g) 합의
- 각자 비밀 (a, b) 선택
- 공개 값 교환 (g^a, g^b)
- 같은 비밀 계산:
- Alice: (g^b)^a = g^ab
- Bob: (g^a)^b = g^ab
도청자가 g^a, g^b를 봐도 a, b 못 구함 (이산 로그 문제).
ECDHE: Elliptic Curve Diffie-Hellman Ephemeral.
- 더 빠름
- 같은 보안에 더 짧은 키
- Ephemeral (매번 새 키) → Forward secrecy
3. TLS 1.2 핸드셰이크
3.1 단계별 흐름
[Client] [Server]
│ │
├──── ClientHello ───────────────────→│
│ [supported ciphers, random] │
│ │
│←─── ServerHello ────────────────────┤
│ [chosen cipher, random] │
│←─── Certificate ────────────────────┤
│←─── ServerKeyExchange ──────────────┤
│←─── ServerHelloDone ────────────────┤
│ │
├──── ClientKeyExchange ─────────────→│
├──── ChangeCipherSpec ──────────────→│
├──── Finished ──────────────────────→│
│ │
│←─── ChangeCipherSpec ───────────────┤
│←─── Finished ───────────────────────┤
│ │
←══════ 암호화된 데이터 ═══════════════→
총 2 RTT (RTT = Round Trip Time).
3.2 단계 설명
1. ClientHello:
- TLS 버전
- 지원 cipher suites
- Random nonce
- SNI (Server Name Indication)
2. ServerHello:
- 선택한 cipher suite
- Random nonce
3. Certificate:
- 서버의 X.509 인증서
4. ServerKeyExchange:
- DH 매개변수 (forward secrecy 위해)
- 서명
5. ClientKeyExchange:
- 클라이언트의 DH 공개값
6. Finished:
- 양쪽이 같은 키를 도출했는지 검증
3.3 Cipher Suite
예시: TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384
분해:
- ECDHE: 키 교환 (Forward Secrecy)
- RSA: 인증 (서명)
- AES_256_GCM: 대칭 암호화 + MAC
- SHA384: 해시
각 부분이 다른 알고리즘 사용.
3.4 TLS 1.2의 문제
- 2 RTT (느림)
- 약한 cipher 지원 (RC4, 3DES, MD5)
- 다운그레이드 공격
- RSA key exchange는 forward secrecy X
4. TLS 1.3 — 혁명
4.1 변화
TLS 1.3 (2018)이 가져온 변화:
- 1-RTT 핸드셰이크
- 0-RTT 재연결
- 약한 cipher 모두 제거
- Forward Secrecy 의무화
- 암호화된 인증서
4.2 단순화된 핸드셰이크
[Client] [Server]
│ │
├──── ClientHello ───────────────────→│ ← 1 RTT
│ [+ key_share, supported_groups]│
│ │
│←─── ServerHello ────────────────────┤
│←─── EncryptedExtensions ────────────┤
│←─── Certificate (encrypted) ────────┤
│←─── CertificateVerify ──────────────┤
│←─── Finished ───────────────────────┤
│ │
├──── Finished ──────────────────────→│
│ │
←══════ 암호화된 데이터 ═══════════════→
TLS 1.2의 절반 RTT.
4.3 0-RTT (Zero Round Trip Time)
재방문 시:
[Client] [Server]
│ │
├──── ClientHello + early_data ─────→│ ← 0 RTT!
│←─── Server Response ────────────────┤
이전 세션의 키 캐시 → 첫 패킷에 데이터 포함.
위험: Replay attack (idempotent 요청만 안전).
4.4 제거된 것들
TLS 1.3에서 제거:
- ❌ RSA key exchange (no forward secrecy)
- ❌ DH (non-ephemeral)
- ❌ MD5
- ❌ SHA-1
- ❌ RC4
- ❌ 3DES
- ❌ DSA
- ❌ Compression
남은 것:
- ✅ ECDHE (forward secrecy)
- ✅ AEAD only (AES-GCM, ChaCha20-Poly1305)
- ✅ SHA-256, SHA-384
4.5 채택률
2025년 현재:
- 70%+ 사이트가 TLS 1.3
- 모든 주요 브라우저 지원
- AWS, Cloudflare 등이 주도
5. 인증서
5.1 X.509 인증서
Certificate:
Version: 3
Serial Number: 12345
Signature Algorithm: ecdsa-with-SHA256
Issuer: CN=Let's Encrypt R3
Validity:
Not Before: 2025-01-01
Not After: 2025-04-01
Subject: CN=example.com
Subject Public Key Info:
Public Key Algorithm: id-ecPublicKey
EC Public Key: 04:A1:B2:...
X509v3 extensions:
X509v3 Subject Alternative Name:
DNS:example.com, DNS:www.example.com
X509v3 Extended Key Usage:
TLS Web Server Authentication
Signature: 30:46:02:21:...
5.2 인증서 체인
[Root CA] (자체 서명, OS/브라우저에 미리 설치)
↓ 서명
[Intermediate CA] (Let's Encrypt R3)
↓ 서명
[Leaf Certificate] (example.com)
브라우저의 검증:
- Leaf 인증서를 받음
- Issuer (Intermediate CA) 확인
- Intermediate가 Root CA로 서명되었는지 확인
- Root가 신뢰 목록에 있는지 확인
5.3 X.509 v3 Extensions
중요한 확장:
- Subject Alternative Name (SAN): 도메인 목록
- Extended Key Usage: 용도 (web server, email 등)
- Basic Constraints: CA인지 leaf인지
- Key Usage: 키 사용 목적
- CRL Distribution Points: 폐기 목록 위치
5.4 Let's Encrypt
무료 인증서 자동화.
# Certbot
sudo certbot --nginx -d example.com -d www.example.com
작동:
- ACME 프로토콜
- 도메인 소유 검증 (HTTP-01, DNS-01)
- 인증서 발급 (90일 유효)
- 자동 갱신
효과: HTTPS의 민주화. 2024년 70%+ 사이트가 Let's Encrypt 사용.
5.5 인증서 폐기
문제: 인증서가 만료 전에 손상되면?
해결:
- CRL (Certificate Revocation List): 폐기 목록 다운로드
- OCSP (Online Certificate Status Protocol): 실시간 확인
- OCSP Stapling: 서버가 OCSP 응답을 함께 전송
- Short-lived certs: 90일로 만료 빨리 (Let's Encrypt)
현실: CRL/OCSP가 잘 작동 안 함. 짧은 만료 기간이 더 효과적.
6. Certificate Transparency
6.1 문제
2011년 DigiNotar 사고: CA가 해킹당해 가짜 Google.com 인증서 발급.
→ 누가 인증서를 발급하는지 추적 필요.
6.2 Certificate Transparency
모든 인증서를 공개 로그에 기록:
- Append-only Merkle tree
- 누구나 검색 가능
- 의심스러운 인증서 감지
예:
# 도메인의 모든 인증서 검색
curl https://crt.sh/?q=example.com
6.3 SCT (Signed Certificate Timestamp)
CA가 인증서를 CT 로그에 제출 → SCT 받음 → 인증서에 포함.
브라우저가 SCT 검증 → 로그에 등록되었는지 확인.
Chrome: 2018년부터 SCT 없는 인증서 거부.
6.4 효과
- 가짜 인증서 빠른 탐지
- CA 책임성 강화
- 사용자가 자신의 도메인 인증서 모니터링
도구:
- crt.sh
- censys.io
- Facebook CT Monitor
7. mTLS (Mutual TLS)
7.1 단방향 TLS의 한계
일반 TLS: 클라이언트가 서버를 인증 (서버 인증서 검증).
문제: 서버가 클라이언트를 모름.
- API 키, OAuth로 별도 인증 필요
- 복잡
7.2 mTLS
양방향 인증: 클라이언트도 인증서 제시.
[Client] ←──── 서버 인증서 ────── [Server]
[Client] ────── 클라이언트 인증서 ───→ [Server]
효과:
- 서버가 클라이언트를 cryptographically 인증
- 별도 인증 메커니즘 불필요
- Zero-trust 네트워크
7.3 사용 사례
1. 서비스 간 통신:
- Service Mesh (Istio, Linkerd)
- 마이크로서비스 zero-trust
2. 디바이스 인증:
- IoT
- 모바일 앱 (인증서 pinning)
3. 엔터프라이즈 VPN:
- 직원 디바이스 인증
4. API 보안:
- B2B API
- 금융 (PCI-DSS)
7.4 구현
Nginx:
server {
listen 443 ssl;
ssl_certificate /etc/ssl/server.crt;
ssl_certificate_key /etc/ssl/server.key;
ssl_client_certificate /etc/ssl/ca.crt;
ssl_verify_client on;
location / {
# 인증서 정보를 backend에 전달
proxy_set_header X-SSL-Client-DN $ssl_client_s_dn;
}
}
Service Mesh (Istio):
- 자동 mTLS
- 사이드카가 처리
- 앱 코드 변경 X
7.5 SPIFFE/SPIRE
SPIFFE: Service identity 표준.
spiffe://example.com/services/payment
SPIRE: SPIFFE의 구현.
효과: 서비스 신원의 표준화. mTLS 자동화.
8. 흔한 함정과 보안
8.1 인증서 검증 누락
잘못:
import requests
requests.get('https://example.com', verify=False) # 위험!
올바름:
requests.get('https://example.com') # 기본 검증
verify=False는 MITM 공격에 노출.
8.2 호스트명 검증
import ssl
import socket
context = ssl.create_default_context()
# 호스트명 검증 활성화 (기본)
context.check_hostname = True
context.verify_mode = ssl.CERT_REQUIRED
with socket.create_connection(('example.com', 443)) as sock:
with context.wrap_socket(sock, server_hostname='example.com') as ssock:
# 검증된 연결
pass
server_hostname 누락: 인증서 검증되지만 도메인 일치 확인 X.
8.3 Cipher 설정
나쁜 설정:
ssl_ciphers RC4:HIGH; # RC4는 취약!
좋은 설정 (Mozilla SSL Config):
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers off;
Mozilla SSL Configuration Generator: https://ssl-config.mozilla.org/
8.4 HSTS
Strict-Transport-Security: max-age=31536000; includeSubDomains; preload
효과: 브라우저가 HTTPS만 사용 강제. HTTP 접근 시 자동 리다이렉트.
preload list: 브라우저에 미리 등록.
8.5 인증서 핀닝
Certificate Pinning: 특정 인증서만 신뢰.
// iOS
let pinnedCertificate = ... // 미리 임베드
let serverCertificate = ... // 받은 인증서
if pinnedCertificate == serverCertificate {
// OK
}
효과: CA가 손상되어도 안전.
단점: 인증서 갱신 시 앱 업데이트 필요.
8.6 알려진 공격
- POODLE (2014): SSL 3.0 → SSL 3.0 폐기
- Heartbleed (2014): OpenSSL 버그 → 패치
- BEAST (2011): TLS 1.0 → TLS 1.0 폐기
- CRIME (2012): TLS 압축 → 압축 비활성화
- Lucky 13 (2013): CBC mode → AEAD 권장
- Logjam (2015): DH 약한 매개변수
- DROWN (2016): SSL 2.0 활성화 → SSL 2.0 폐기
교훈: 최신 TLS 사용. 알려진 약점 회피.
9. Post-Quantum 암호
9.1 위협
양자 컴퓨터의 등장:
- Shor's algorithm: RSA, ECC를 다항 시간에 깨뜨림
- 충분히 큰 양자 컴퓨터 = 모든 비대칭 암호 무력화
현재: 양자 컴퓨터가 아직 약함 (수십 큐비트). 미래: 2030~2040년 위협 가능성.
9.2 NIST 표준화
2022년: NIST가 PQC 알고리즘 선정.
선정된 알고리즘 (2024):
- CRYSTALS-Kyber: 키 캡슐화 (FIPS 203)
- CRYSTALS-Dilithium: 디지털 서명 (FIPS 204)
- SPHINCS+: 해시 기반 서명 (FIPS 205)
- FALCON: 격자 기반 서명
9.3 Hybrid Mode
현재 전환 전략: 고전 + PQC 결합.
TLS Key Exchange:
ECDHE (고전) + Kyber (PQ)
효과:
- 양쪽 다 안전해야 키 보호
- 점진적 전환
채택:
- Cloudflare: 2022년부터 Kyber 실험
- Google Chrome: 2024년 hybrid Kyber 활성화
- Apple iMessage: PQ3 (2024)
9.4 Harvest Now, Decrypt Later
위협 시나리오:
- 공격자가 지금 암호화된 트래픽 저장
- 미래에 양자 컴퓨터로 복호화
대응: 지금부터 PQ 암호 사용.
특히 장기 비밀 (정부, 의료, 금융)은 즉시 마이그레이션 필요.
10. 실전 — TLS 운영
10.1 인증서 모니터링
# 만료일 확인
echo | openssl s_client -connect example.com:443 2>/dev/null \
| openssl x509 -noout -dates
# 만료까지 일수
echo | openssl s_client -connect example.com:443 2>/dev/null \
| openssl x509 -noout -enddate \
| cut -d= -f2 \
| xargs -I {} date -d {} +%s
도구:
- Prometheus exporter (blackbox_exporter)
- Datadog: SSL certificate monitoring
- AWS Certificate Manager: 자동 갱신
10.2 SSL Labs 테스트
https://www.ssllabs.com/ssltest/analyze.html?d=example.com
평가 항목:
- 프로토콜 버전
- Cipher suite
- 인증서 유효성
- HSTS
- Forward Secrecy
- 알려진 취약점
목표: A 또는 A+.
10.3 자동 갱신
Certbot:
# Cron job
0 0 * * * certbot renew --quiet
Kubernetes (cert-manager):
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
name: example-com-tls
spec:
secretName: example-com-tls
issuerRef:
name: letsencrypt-prod
kind: ClusterIssuer
dnsNames:
- example.com
- www.example.com
자동 발급, 갱신, 배포.
10.4 성능 최적화
1. Session Resumption:
- Session ID
- Session Tickets
2. OCSP Stapling:
- 서버가 OCSP 응답 캐시
- 클라이언트의 OCSP 요청 절약
3. HTTP/2 / HTTP/3:
- 멀티플렉싱
- 연결 재사용
4. ALPN:
- HTTP/2 협상
5. 0-RTT (TLS 1.3):
- 재방문 시 latency 0
퀴즈
1. TLS 1.3이 TLS 1.2보다 좋은 점은?
답: (1) 1-RTT 핸드셰이크 (TLS 1.2는 2-RTT) — 빠른 연결, (2) 0-RTT 재연결 — 재방문 시 latency 0, (3) 약한 cipher 모두 제거 — RSA, MD5, SHA-1, RC4, 3DES, DH, 압축 등, (4) Forward Secrecy 의무화 — ECDHE만 허용, (5) 암호화된 인증서 — 메타데이터 보호. 2018년 RFC 8446. 2025년 70%+ 사이트가 TLS 1.3 사용.
2. Forward Secrecy가 왜 중요한가요?
답: 서버의 개인 키가 미래에 유출되어도 과거 통신은 복호화 불가능. ECDHE (Elliptic Curve Diffie-Hellman Ephemeral)를 사용하면 매 세션마다 새 키 생성 → 한 키가 깨져도 다른 세션 안전. 반대 예: RSA key exchange는 서버 키로 모든 세션 키 보호 → 서버 키 유출 시 모든 과거 통신 복호화 가능. TLS 1.3은 forward secrecy 의무화. "Harvest Now, Decrypt Later" 공격 대비.
3. 인증서 체인이 어떻게 작동하나요?
답: Root CA → Intermediate CA → Leaf Certificate 순서. (1) Root CA: 자체 서명, OS/브라우저에 미리 설치 (예: DigiCert, Let's Encrypt), (2) Intermediate CA: Root가 서명, (3) Leaf: Intermediate가 서명 (실제 사이트 인증서). 검증: 브라우저가 leaf → intermediate → root까지 따라가면서 각 서명 검증. Root가 신뢰 목록에 있으면 OK. Why intermediate? Root CA를 오프라인 보호하면서 자주 발급 가능.
4. mTLS가 일반 TLS와 다른 점은?
답: 일반 TLS는 클라이언트가 서버만 인증 — 서버 인증서 검증. mTLS는 양방향 인증 — 클라이언트도 인증서 제시. 결과: 서버가 클라이언트를 cryptographically 인증, API 키나 OAuth 같은 별도 인증 불필요. 사용: (1) Service Mesh (Istio, Linkerd)의 서비스 간 통신, (2) IoT 디바이스 인증, (3) Zero-trust 네트워크, (4) 금융/엔터프라이즈 API. SPIFFE/SPIRE가 service identity 표준.
5. Post-Quantum 암호가 왜 지금 중요한가요?
답: Harvest Now, Decrypt Later 공격. 공격자가 지금 암호화된 트래픽을 저장해두고, 미래에 양자 컴퓨터로 복호화. 양자 컴퓨터의 Shor's algorithm이 RSA, ECC를 다항 시간에 깨뜨릴 수 있음. NIST가 2024년 PQ 알고리즘 표준화: CRYSTALS-Kyber (키 교환), Dilithium (서명). Hybrid mode (고전 + PQ 결합)로 점진적 전환. Cloudflare, Google Chrome이 이미 활성화. 장기 비밀(정부, 의료, 금융)은 즉시 마이그레이션 필요.
참고 자료
현재 단락 (1/418)
- **TLS = 인터넷 보안의 기반**: HTTPS, gRPC, 모든 보안 통신