티스토리 뷰

Dev/HTTP

https, 대칭키, 비대칭키

kjyyjk 2026. 3. 18. 20:26

학습 배경

최근 블로그 클론코딩(리버스 엔지니어링)을하며 nginx에 https를 설정하는 작업을 했다.

이전 프로젝트부터 https를 몇 번 다뤘지만 한번도 내부를 들여다 본 적이 없어 이번 기회에 알아보았다.

 

https란?

패킷을 평문으로 송신하는 http와 다르게 https는 암호화하여 송신한다.

암호화 되어있기 때문에 패킷 송신 중 누군가가 탈취/감청을 해도 패킷의 내용을 알 수가 없다.

 

https 통신에서는 클라이언트가 패킷을 암호화하여 송신하면 서버가 이를 수신하고 복호화한다.

(응답 시에는 그 반대)

 

데이터를 암호화/복호화하기 위해서는 키가 필요하다.

https를 알아보기 위해서는 대칭키와 비대칭키에 대해 알아야한다.

 

대칭키는 하나의 키를 가지고 암/복호화를 모두 할 수 있다. 말그대로 대칭이다.

반대로 비대칭키는 암호화하는 키(공개키)와 복호화하는 키(개인키)가 별도로 존재한다.

공개키를 가진 자는 암호화만할 수 있고 복호화는 하지 못한다.(반대도 가능하다)

 

클라이언트와 서버 간의 통신에서는 어떤 종류의 키를 사용하던 양쪽 모두 키를 가지고 있어야 통신할 수 있을 것이다.

 

키는 어떻게 교환할 것인가?

만약 대칭키를 평문으로 주고 받았다간 탈취되어 누구나 암호화 된 데이터를 들여다볼 수 있게 된다.

 

이러한 문제를 해결하기 위해 https는 TLS 핸드쉐이크 과정에서 안전하게 키를 교환하며,

그 방법으로는 다음 두 가지가 있다.

 

대칭키를 공개키로 암호화하여 전달

서버는 ServerHello 과정에서 인증서와 함께 공개키를 전달한다.

공개키로 암호화한 데이터는 개인키로만 복호화할 수 있기 때문에 탈취되어도 안심해도 된다.

클라이언트는 SSL 인증서를 검증한 뒤, 대칭키를 생성하고 서버에게 전달 받은 공개키로 암호화하여 서버로 전달한다.

암호화된 대칭키는 서버만 알고 있는 개인키로 복호화할 수 있기 때문에 제 3자는 대칭키를 알 수 없게 된다.

서버는 클라이언트로부터 전달 받은 대칭키를 개인키로 복호화한다.

이로써 클라이언트와 서버 모두 동일한 대칭키를 가지게 되었고, TLS 핸드쉐이크 종료 후 암호화된 데이터를 주고 받으며 통신한다.

 

본 방식의 단점은 암호화된 대칭키가 네트워크를 탄다는 것이다.

만약 서버의 개인키가 유출되면 제 3자가 이전에 통신에서 사용했던 대칭키와 데이터 모두 확인이 가능하다. 

이러한 보안 문제로 TLS 1.3 버전부터는 본 방식을 지원하지 않는다.

 

디피헬만 알고리즘을 활용한 대칭키 공유

우선 디피헬만 알고리즘을 간단히 설명하자면 다음과 같다.

- 공통값 g와 개인 값 a, b가 존재

- (g^a)^b = (g^b)^a = x

- (g^a), (g^b)를 모두 알고 있어도 x를 유추하는 것이 불가능하다.

- 정확히는 공통 값 g와 p가 존재하고 (g^a) mod p와 같은 구조이지만 본 글에서는 간략하게 표현한다.

 

클라이언트와 서버는 이러한 원리를 이용해 대칭키를 공유한다.

클라이언트는 ClientHello 과정에서 자신의 비밀값(a)으로 생성한 중간값(g^a)을 서버로 전달한다.

서버는 ServerHello 과정에서 인증서와 함께 자신의 비밀값(b)으로 생성한 중간값(g^b)을 클라이언트로 전달한다.

클라이언트는 서버로부터 전달 받은 인증서를 검증한다.

서로가 생성한 중간값을 전달 받은 클라이언트와 서버는 자신의 비밀값을 이용해 대칭키(x = (g^a)^b = (g^b)^a)를 생성한다. 

 

이로써 클라이언트와 서버는 동일한 대칭키(x)를 가지며 TLS 핸드쉐이크 과정을 마치고,

이 대칭키를 활용해 암호화된 데이터를 주고 받으며 통신한다.

 

앞서 본 공개키 암호화 방식과 다르게 키 값이 네트워크를 타지 않는다는 것이 장점이다.

이러한 보안적 이점 덕분에 TLS 1.3 버전에서는 본 방식을 채택하고 있다.

 

위에서 살펴본 두 가지 키 교환 방식에는 공통점이 있다.

대칭키를 교환하는 방식만 다를 뿐, 본 통신에서는 비대칭키가 아닌 대칭키를 사용한다는 것이다.

 

왜 본 통신에는 대칭키를 사용할까?

서버의 cpu 연산 비용 때문이다.

비대칭키는 a로 암호화한 데이터를 b로만 복호화할 수 있는 것과 같이 비대칭 알고리즘의 복잡한 수식에 기반을 가지고 있다.

그렇기에 비대칭 키를 이용하여 복호화 하는 것은 cpu 관점에서 비용이 비싸다. 

특히 N:1 구조의 클라이언트-서버 구조에서 서버가 비대칭키로 복호화하는 것은 비효율적이다.

 

반대로 대칭키는 a로 암호화하고 a로 복호화할 수 있는 단순하고 저렴한 구조이다.

그렇기 때문에 서버 부하 관점에서 비대칭키보다 효율적인 대칭키를 사용하는 것이다.

'Dev > HTTP' 카테고리의 다른 글

Certbot, CA, SSL 인증서  (0) 2026.03.28
[HTTP] HTTP 헤더 (3)  (0) 2023.01.03
[HTTP] HTTP 헤더 (2)  (0) 2022.12.29
[HTTP] HTTP 헤더 (1)  (2) 2022.12.29
[HTTP] HTTP 상태코드  (0) 2022.12.27
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2026/04   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30
글 보관함