4강 / 20강
비밀번호는 어떻게 저장해야 하나
해시 · 솔트 · 그리고 '일부러 느린' 해시
회원가입을 받으면 비밀번호를 저장해야 합니다. 그런데 어떻게 저장할까요? 가장 순진한 방법 — 입력한 그대로 DB에 넣는 것 — 은 최악입니다. DB가 한 번 새면(11강에서 실제로 뚫어 봅니다) 모든 회원의 비밀번호가 그대로 유출되거든요.
정답은 뜻밖입니다. 비밀번호를 저장하지 않는 것입니다. 대신 해시라는, 되돌릴 수 없는 지문만 저장합니다.
해시는 되돌릴 수 없는 지문입니다
해시 함수는 어떤 입력이든 정해진 길이의 값으로 바꿉니다. 특징이 둘이에요.
- 같은 입력 → 항상 같은 출력 (그래서 로그인 확인에 쓸 수 있다)
- 한 글자만 바꿔도 → 완전히 다른 출력 (눈사태 효과)
- 출력 → 입력으로 되돌리기 불가능 (단방향)
직접 확인해 봅시다.
결과 아래 '눈사태 효과' 설명을 보세요.
🖥️ 내 가상 서버
브라우저 안에서 실행 (계산용)
브라우저 안에서 직접 해시해 봅니다.
Python
브라우저 안에서 실행 (계산용)
로그인은 이렇게 이뤄집니다
서버는 여러분의 비밀번호를 모릅니다. 그럼 어떻게 로그인을 확인할까요?
가입할 때
입력한 비번을 해시해서 그 해시만 저장. 원본은 버림
로그인할 때
입력한 비번을 같은 방법으로 해시해서, 저장된 해시와 같은지만 비교
그래서 서버가 뚫려도 공격자가 얻는 것은 해시뿐입니다. 원본 비밀번호가 아니에요. … 라고 하고 싶지만, 여기에 두 가지 함정이 있습니다.
직접 봅시다. 서버가 뚫려 /etc/shadow(비밀번호 해시가 든 파일)가
새어 나갔다고 상상하고, 공격자가 그것으로 무엇을 하는지 봅니다.
각 해시 맨 앞의 $1$ / $6$ / $2b$ 가 알고리즘 표시입니다.
🖥️ 내 가상 서버
브라우저 안에서 실행 (계산용)
어떤 계정이 몇 초 만에 깨지는지 보세요.
🖥️ 내 가상 서버
브라우저 안에서 실행 (계산용)
🤔 확인 문제
서버 DB가 유출됐는데, 비밀번호가 솔트를 넣은 bcrypt 해시로 저장돼 있었습니다. 공격자는?
해설 솔트가 있어 미리 만든 표가 안 통하고(계정마다 해시가 다름), bcrypt 라 대입이 느립니다. '해시를 복호화한다'는 건 존재하지 않는 개념이에요 — 해시는 단방향입니다.
🤔 확인 문제
비밀번호 저장에 SHA-256 을 쓰면 안 되는 이유로 가장 정확한 것은?
해설 SHA-256 은 튼튼하지만 빠르라고 만든 해시입니다. 파일 무결성 확인엔 좋지만, 비밀번호엔 느린 해시(bcrypt 등)를 써야 대입 공격이 비싸집니다.