본문 바로가기
안드로이드/etc.

[CS] 대칭키와 비대칭키(공개키) 암호화 방식

by jinwo_o 2024. 9. 11.

암호화 기술

  • 암호화는 데이터를 읽을 수 없는 형태로 변환하는 과정이다. 이를 통해 데이터가 전송 중에 도청되더라도 내용을 알 수 없게 된다.
  • 즉, 암호화 기술을 통해 데이터를 암호화하면, 해당 데이터를 읽을 수 있는 사람을 제한할 수 있기 때문에 데이터의 기밀성을 보장한다.
  • HTTPS 와 같은 보안 프로토콜에서는 대칭키와 공개키 암호화를 결합하여 사용한다.
    • 대칭키 암호화의 장점과 공개키 암호화의 장점을 채택하여 용량이 큰 정보는 대칭키로 암호화하고, 암호화에 사용된 대칭키는 공개키로 암호화하여 대상에게 전달하는 하이브리드 암호화 방법이 일반적으로 사용되고 있다.

 

대칭키 암호화 방식

  • 암호화와 복호화에 같은 키를 사용하는 방식으로, 암호화한 정보를 다른 사용자에게 보낼 때 암호 키도 함께 보내야 한다.
  • 구현이 간단하고, 단일 키를 사용하기 때문에 암호화와 복호화 과정에서 발생하는 계산 복잡도가 낮아 암호화와 복호화 과정이 빠르다. 따라서 대량의 데이터를 암호화해야 하는 상황에서 유용하다.
  • 하지만 암호화와 복호화에 같은 키를 사용하고, 암호화된 데이터를 주고받는 모든 당사자가 같은 키를 공유해야 하기 때문에 키 관리의 어려움이 있다.
  • 키가 암호화가 되지 않은 평문으로 분실되거나 타인에게 노출되면 보안에 매우 취약해진다.
  • 네트워크 통신, 파일 암호화 등에 활용된다.
  • 대표적으로 높은 보안성을 제공하는 AES(Advanced Encryption Standard) 알고리즘이 있다.
import javax.crypto.Cipher
import javax.crypto.KeyGenerator
import javax.crypto.SecretKey

fun main() {
    val keyGen = KeyGenerator.getInstance("AES")
    keyGen.init(128)
    val secretKey: SecretKey = keyGen.generateKey()

    val cipher = Cipher.getInstance("AES")
    cipher.init(Cipher.ENCRYPT_MODE, secretKey)
    val encrypted: ByteArray = cipher.doFinal("Hello, World!".toByteArray())

    println("Encrypted: ${encrypted.joinToString("") { String.format("%02x", it) }}")
}

 

비대칭키(공개키) 암호화 방식

  • 암호화와 복호화에 서로 다른 키를 사용하는 방식
  • 공개키와 개인키라는 두 가지 키가 사용된다. 공개키는 누구에게나 공개될 수 있으며, 개인키는 소유자만이 보유한다.
  • 공개키로 데이터를 암호화하고, 개인키로만 데이터를 복호화할 수 있기 때문에, 데이터 전송 과정에서의 보안성과 안전성이 매우 높다.
  • 두 개의 키를 사용하고 복잡한 수학적 연산을 필요로 하기 때문에 계산 복잡도가 높아, 암호화와 복호화 과정이 대칭키 방식에 비해 느리다. 따라서 대량의 데이터를 암호화하는 데에는 적합하지 않다.
  • 공개키는 안전하게 공유될 수 있고, 개인키는 소유자만 관리하면 되기 때문에 키 관리가 용이하다.
  • 개인키는 암호화된 데이터를 복호화하는 데 사용되기 때문에, 개인키의 보안이 암호화 시스템의 전체 보안을 결정짓는 중요한 요소이다.
  • 디지털 서명, SSL/TLS와 같은 보안 통신, 데이터베이스 암호화 등에 활용된다.
  • 대표적으로 인터넷 상에서 안전한 데이터 전송을 위해 널리 사용되고 있는 RSA(Rivest-Shamir-Adleman) 알고리즘이 있다.
import java.security.KeyPair
import java.security.KeyPairGenerator
import javax.crypto.Cipher

fun main() {
    val keyGen = KeyPairGenerator.getInstance("RSA")
    keyGen.initialize(2048)
    val keyPair: KeyPair = keyGen.generateKeyPair()

    val cipher = Cipher.getInstance("RSA")
    cipher.init(Cipher.ENCRYPT_MODE, keyPair.public)
    val encrypted: ByteArray = cipher.doFinal("Hello, World!".toByteArray())

    // 바이트 배열을 16진수 문자열로 변환하여 출력
    println("Encrypted: ${encrypted.joinToString("") { String.format("%02x", it) }}")
}

 

공개키 암호화 방식의 진행과정

  1. 서버는 자신의 공개키를 공개한다. 이 공개키는 암호화에 사용되는 키이며, 누구든지 열람이 가능하다. (복호화에 사용되는 키는 서버만 가지고 있다. 잃어버리면 안된다)
  2. 클라이언트는 서버의 공개키로 데이터를 암호화한다.
  3. 클라이언트는 암호화된 문서를 서버에게 전송한다.
  4. 서버는 자신만의 개인키(복호화키)를 이용하여 전송받은 암호화 문서를 복호화하여 데이터를 열람한다.

 

개인키 암호화 방식

  • 개인키로 암호화하는 것은 이 개인키를 가진 소유자만이 할 수 있는 일이기 때문에 지문처럼 사용된다.
  • 공개키를 가진 누구든지 암호문을 복호화할 수 있다.
  • 암호화로서의 의미보다, 누가 메시지를 썼는지 알려주고 그 메시지가 위조되지 않았음을 증명할 수 있다. (디지털 서명)

 

공개키 암호화 방식의 문제점

  • 만약 클라이언트가 키를 사용하는 직전에 누군가에 의해 교체됐다면, 공개키가 진짜인지 아닌지를 증명할 수 있는 방법이 없다.
  • 또는 클라이언트가 사용하고자 하는 서버의 공개키가 진짜 서버의 것인지 알 수 없다.
  • 해결책 : 클라이언트와 서버 모두가 믿을만한 제 3자인 CA 인증 기관의 도움이 필요하다.
    • CA(Certificate Authority) : '서버가 진짜 믿을만한 사이트다' 라는 어떤 인증서를 발행해주는 역할을 한다.

 

CA 인증서 발행 과정

  1. 서버는 인증 기관에 서버의 공개키와 사이트 정보를 전송한다.
  2. 인증 기관은 사이트를 검증한 후 인증 기관의 개인키로 서명한다.
  3. 인증 기관은 사이트 인증서(SSL 인증서, 디지털 서명)를 서버에게 전송한다.
  4. 서버는 클라이언트에게 사이트 인증서를 전송한다.
  5. 클라이언트는 인증서가 진짜인지를 확인하기 위해 복호화에 필요한 공개키를 인증 기관에 요청한다.
  6. 인증 기관은 클라이언트에게 인증 기관의 공개키를 전송한다.
    • 사용자의 브라우저 내에 대표적인 CA 목록이 내장되어 있기 때문에 5, 6번 과정은 생략해도 된다.
  7. SSL 인증서를 인증 기관의 공개키로 검증한다.

 

대칭키와 비대칭키 암호화 방식의 이해

대칭키와 비대칭키 암호화 방식의 기본 개념, 특징 및 장단점을 비교하고, 각 방식의 적절한 사용 상황에 대해 설명합니다.

f-lab.kr

 

암호화 기술의 기초: 대칭키와 비대칭키

대칭키와 비대칭키 암호화 기술의 기본 개념과 활용 방법에 대해 설명하는 글입니다.

f-lab.kr

 

HTTPS와 대칭키 및 비대칭키 암호화의 이해

이 글은 HTTPS와 대칭키 및 비대칭키 암호화의 기본 개념을 설명하고, 이를 실제로 적용하는 방법을 다룹니다. HTTPS의 동작 원리와 보안 메커니즘을 이해하고, 대칭키와 비대칭키 암호화의 장단점

f-lab.kr

 

Ready-For-Tech-Interview/Network/공개키 & 대칭키.md at master · WooVictory/Ready-For-Tech-Interview

💻 신입 개발자로서 지식을 쌓기 위해 공부하는 공간 👨‍💻. Contribute to WooVictory/Ready-For-Tech-Interview development by creating an account on GitHub.

github.com

https://youtu.be/8BNx8UbAo2s?si=UzbG6Cq9_mDBukFg

'안드로이드 > etc.' 카테고리의 다른 글

[CS] HTTP와 HTTPS  (0) 2024.09.14
[CS] Database 인덱스 (Index)  (0) 2024.09.09
[CS] 캐시 (Cache)  (0) 2024.09.04