암호화 - 단방향

1. 단방향 해시 함수

사용자의 비밀번호를 암호화할 때는 단방향 해시 함수(one-way hash function)가 일반적으로 쓰인다.
이름에서 알 수 있듯이 단방향 해시 함수는 복호화를 할 수 없는 암호화 알고리즘이다.
즉, 사용자의 비밀번호를 데이터베이스에 저장할 때는 복호화할 목적으로 저장하지 않고,
온전히 본래의 비밀번호 값을 알지 못하도록 방지하는데에 목적이 있는 것이다.

  • 예시
    • test password 라는 값을 hash256 단방향 해시 함수를 사용하면 0b47c68b1.....094e 값이 나온다.
    • 그리고 이 해시 값(암호화된 값)은 원본 비밀번호 값인 test password 로 복호화 될 수 없다.
    • 그러므로 원본 메시지를 알면 암호화된 메시지를 구하기는 가능하나, 암호화된 메시지로는 원본 메시지를 구할수 없어서 단방향성 이라고 한다.

1.1 파이썬으로 구현

import hashlib

m = hashlib.sha256()		# sha256 알고리즘 선택
m.update(b"test password")	# 바이트 값 입력
m.hexdigest()				# 암호화된 값을 hex(16진수) 값으로 읽어 들인다.

0b47c68b1.....094e

2. 해킹... 그리고 보안

해시함수

해시 함수는 원래 패스워드를 저장하기 위해 설계된 것이 아니라 짧은 시간에 데이터를 검색하기 위해 설계된 것이기 때문에 속도가 빠르다.
딕셔너리(dict), 세트(set) 자료구조에 해시가 쓰인다.
그렇게 때문에 해시 함수는 본래 처리 속도가 최대한 빠르도록 설계되었다.

취약점 보안

단방향 해시함수도 rainbow attack 이라는 해킹방법에 의해 해킹당할 수가 있다.
이러한 해킹에 대한 취약점을 보안하기 위해 일반적으로 2가지 보완점들이 사용된다.
1. salting
2. key stretching

2.1 salting

실제 비밀번호 이외에 추가적으로 랜덤 데이터를 더해서 해시 값을 계산하는 방법
본래 비밀번호에 랜덤 값을 더해서 해시화를 하기 때문에 혹시나 해킹당한 경우에도 해커가 실제로
어느 부분이 실제 비밀번호 값이고, 어느 부분이 랜덤값인지 알 수 가 없게 된다.
그러므로 rainbow attack 처럼 미리 해시 값들을 계산하여 해킹하는 공격들을 무효화할 수 있다.

2.2 key stretching

기존 단방향 해시 알고리즘들의 실행 속도가 너무 빠르다는 취약점을 보완하기 위해서,
단방향 해시 값을 계산한 후 그 해시 값을 또 해시하고, 이를 여러 번 반복하는 방법이 키 스트레칭(key stretching) 이다.
즉, 여러 번 해시 함수를 적용시켜서 해시값을 계산하는 것이다. 일반적인 장비로 1초에 50억 개 이상의 해시 함수를 실행시킬 수 있지만,
키 스트레칭을 적용하여 동일한 장비에서 1초에 5번 정도만 가능하다. GPU를 사용하더라도 수백에서 수천 번 정도만 실행 가능하다.
50억 번과는 비교할 수도 없을 정도로 적은 횟수다. 앞으로 컴퓨터 성능이 더 향상되더라도 키 스트레칭에서 해시 실행을 반복하는 횟수를 추가하여 계속해서
보완할 수 있다는 장점이 있다.

3. bcrypt

salting 과 key stretching 을 구현한 해시 함수 중에서 가장 널리 사용되는 것이 bcrypt 이다.
bcrypt는 처음부터 비밀번호를 단방향 암호화하기 위해 만들어진 해시 함수다.
그러므로 인증 엔드포인트를 구현할 때 bcrypt 알고리즘을 사용하는 편이다.

3.1 설치

pip install bcrypt

3.2 사용

import bcrypt

bcrypt.hashpw(b"secrete password", bcrypt.gensalt())  # hashpw("비번", "salt값")
bcrypt.hashpw(b"secrete password", bcrypt.gensalt()).hex()  # 16진수로 값을 본다.

좋은 웹페이지 즐겨찾기