5. Passwords

추측하기 쉬운 비밀번호를 사용한다든지, 똑같은 비밀번호를 여러 계정에 사용하면 하나의 계정만 뚫려도 여러 계정에 여파가 미치기 때문에 꽤나 심각한 보안 문제라는 것이 알려지고 있다. 만약 해커가 당신의 비밀번호의 hash를 알아냈다면, 당신은 그 hash 값을 통해 본래 비밀번호로 되돌리기가 매우 어렵기를 원한다. 혹여라도 본래 비밀번호로 되돌려졌다면, 그 비밀번호는 다른 계정에도 쓰이지 않아서 다른 곳에 여파가 미치지 말아야 한다.

이러한 인식 덕분에 비밀번호 관리자가 등장하게 되었다. 비밀번호 관리자는 비밀번호를 안전하게 생성 및 저장하고 불러올 수 있으며, 마스터 비밀번호나 passphrase를 통해서 암호화시키는 도구이다. KeePass와 같이 local에 저장하는 프로그램도 있고, LastPass처럼 웹서비스에 저장하는 도구도 있다. 이러한 도구들 모두 좋은 도구들이고, GNU/Linux에서도 잘 작동한다. 필자 개인적으로는 LastPass에 대해서는 회의적인데, 일단 third party 서비스에 내 비밀번호를 저장하고 싶지 않기도 할 뿐 더러, 나는 JavaScript 암호화를 믿지 않기 때문이다.

재밌게도, 암호화를 위해서 우리가 가진거라곤 작디 작은 GnuPG 환경 뿐이기 때문에 이러한 환경에서 가질 수 있는 하나의 선택권은 pass(1)로, 스스로를 “the standard UNIX password manager”라고 지칭하는 도구이다. 이 프로그램을 단순화시켜서 설명하자면, git(1), gpg2(1), pwgen(1), tree(1), xclip(1)과 당신이 원하는 $EDITOR를 둘러싼 약간의 bash(1) 자동완성을 가진 shell script라고 볼 수 있다. 당신이 이미 기존의 비밀번호 관리 방법에 대해서 조사를 좀 해봤다면 알겠지만, 이 프로그램은 명령줄에서 (따라서 SSH에서도) 접근할 수 있는 안전한 비밀번호 저장소를 위한 minimal approach를 제공하기 때문에 새로운 암호화 환경을 설정하는 첫 프로그램으로 딱 좋다.

이 프로그램은 Debian 계열의 시스템에서 pass package에 포함되어 있다.

# apt-get install pass

그리고 매뉴얼도 포함하고 있다.

$ man pass

다른 운영체제에서 설치하고자 한다면 프로그램 웹사이트에서 설명을 찾아볼 수 있다. 배포판을 직접 다운로드하고자 한다면 개발 저장소에 가보길 바란다. 배포판을 다운받아서 직접 쓸 거라면, 필수 프로그램들이 모두 설치되어 있는지 확인하자. 다만 X Windows 시스템에서는 xclip(1)만이 필수적이다.



Setup

아무 argument 없이 pass(1)를 호출해서 현황을 볼 수 있다.

$ pass

우리의 비밀번호 저장소를 initialize 해보자. 당신이 사용할 비밀번호를 저장하려면, root가 아닌 당신 소유의 계정으로 작업해야 한다. 왜냐하면 pass(1)가 자체적으로 암호화하기 위해서 GnuPG를 사용하기 때문에, 프로그램이 사용해야 하는 적절한 key의 ID를 알려줘야 하기 때문이다. 기억나는가? 이 8자리 hex 코드 ID는 gpg --list-secret-keys를 통해서 알 수 있다. 뿐만 아니라 private key를 유일하게 특정지을 수 있는 name이나 이메일 주소 역시 사용할 수 있다.

$ pass init 0x77BB8872
mkdir: created directory ‘/home/tom/.password-store’
Password store initialized for 0x77BB8872.

정말로 ~/.password-store가 생성되었다. 하지만 그 안에는 우리의 key ID를 가지고 있는 .gpg-id 파일 말고는 아무 것도 없다.

$ find .password-store
.password-store
.password-store/.gpg-id



저장하기

이미 사용하고 있는 비밀번호는 pass insert로 저장할 수 있다. 아래처럼 계층 정보도 같이 줄 수 있다.

$ pass insert google.com/gmail/example@gmail.com
mkdir: created directory ‘/home/tom/.password-store/google.com’
mkdir: created directory ‘/home/tom/.password-store/google.com/gmail’
Enter password for google.com/gmail/example@gmail.com:
Retype password for google.com/gmail/example@gmail.com:

비밀번호는 명령줄에서 직접 읽혀져서 암호화되고 ~/.password-store에 저장된다.

$ find .password-store
.password-store
.password-store/google.com
.password-store/google.com/gmail
.password-store/google.com/gmail/example@gmail.com.gpg
.password-store/.gpg-id

이 과정에서 pass(1)는 입력한 계층에 따라 알아서 디렉토리 구조를 생성해준다. 다시 pass로 현황을 깔끔하게 볼 수 있다.

$ pass
Password Store
└── google.com
    └── gmail
            └── example@gmail.com



생성하기

새롭게 랜덤한 비밀번호를 생성하고 싶다면 마지막 argument로 원하는 비밀번호의 길이를 넣어서 generate하면 된다.

$ pass generate google.com/gmail/example@gmail.com 16
The generated password to google.com/gmail/example@gmail.com is:
!Q%i$$&q1+JJi-|X

비밀번호가 기호가 들어가서는 안 된다면, -n 옵션을 넣어주면 된다.

$ pass generate -n google.com/gmail/example@gmail.com 16
The generated password to google.com/gmail/example@gmail.com is:
pJeF18CrZEZzI59D

pass(1)은 비밀번호 생성을 위해 pwgen(1)을 사용한다. 생성한 비밀번호는 자동적으로 비밀번호 저장소에 저장된다.

기존 비밀번호를 변경하고 싶다면 insert를 다시 실행해서 덮어쓰거나, edit을 통해 당신의 $EDITOR에서 변경하도록 할 수도 있다.

$ pass edit google.com/gmail/example@gmail.com

edit의 경우 조심해야 할 것이 있는데, 당신의 $EDITOR가 백업 또는 swap 파일을 plain text 형식으로 임시 디렉토리나 메모리 파일시스템에 저장하도록 설정해두어서는 안 된다는 것이다. Vim의 경우에는 필자가 이를 해결하기 위해 플러그인을 만들어두었다.

비밀번호를 추가하거나 덮어쓰는 작업은 passphrase를 필요로 하지 않고, 비밀번호를 불러오거나 편집할 때만 필요로 하는데, 이는 보통 GnuPG가 작동하는 방식과 일치한다.



불러오기

제대로 passphrase를 입력한다면, 저장된 비밀번호는 다시 불러와져서 명령줄에 echo된다.

$ pass google.com/gmail/example@gmail.com
(...gpg-agent pinentry prompt...)
Tr0ub4dor&3

X windows 시스템에서 xclip(1)이 설치되어 있다면, 비밀번호를 출력하는 대신 클립보드에 바로 저장할 수도 있다.

$ pass -c google.com/gmail/example@gmail.com
Copied google.com/gmail/example@gmail.com to clipboard. Will clear in 45 seconds.

만일 bash 자동완성 기능이 설치되어서 작동하고 있다면, 비밀번호의 계층 구조를 전부 타이핑하는 대신 Tab 키를 통해 자동완성시킬 수 있다. 터미널에서 경로를 이동하듯이 말이다.



삭제하기

더 이상 사용하지 않는 비밀번호는 pass rm을 통해 지울 수 있다.

$ pass rm google.com/gmail/example@gmail.com
Are you sure you would like to delete google.com/gmail/example@gmail.com? [y/N] y
removed ‘/home/tom/.password-store/google.com/gmail/example@gmail.com.gpg’

pass rm -r로 해당 디렉토리에 있는 모든 비밀번호를 지울 수도 있다.

$ pass rm -r google.com
Are you sure you would like to delete google.com? [y/N] y
removed ‘/home/tom/.password-store/google.com/gmail/example@gmail.com.gpg’
removed directory: ‘/home/tom/.password-store/google.com/gmail’
removed directory: ‘/home/tom/.password-store/google.com’



Version Control

To keep historical passwords, including deleted ones if we find we do need them again one day, we can set up some automatic version control on the directory with pass git init: 비밀번호 변경 및 삭제 등의 모든 이력을 간직해서 나중에 지웠던 비밀번호도 다시 찾아보고 싶다면, pass git init을 통해서 해당 경로의 version control을 자동적으로 설정할 수 있다.

$ pass git init
Initialized empty Git repository in /home/tom/.password-store/.git/
[master (root-commit) 0ebb933] Added current contents of password store.
 1 file changed, 1 insertion(+)
 create mode 100644 .gpg-id

이제 비밀번호 저장소에서 뭔가 변경될 때마다 version control repository도 같이 업데이트 될 것이다. 이는 확실하게 우리가 변경하거나 지웠던 예전 비밀번호들을 다시 불러올 수 있음을 의미한다.

$ pass insert google.com/gmail/newexample@gmail.com
mkdir: created directory ‘/home/tom/.password-store/google.com’
mkdir: created directory ‘/home/tom/.password-store/google.com/gmail’
Enter password for google.com/gmail/newexample@gmail.com:
Retype password for google.com/gmail/newexample@gmail.com:
[master 00971b6] Added given password for google.com/gmail/newexample@gmail.com to store.
 1 file changed, 0 insertions(+), 0 deletions(-)
 create mode 100644 google.com/gmail/newexample@gmail.com.gpg



Backups

비밀번호 파일들은 오직 당신의 GnuPG key만을 통해서 암호화되어 있기 때문에, 단순히 ~/.password-store 디렉토리를 복사해서 다른 곳에 저장하는 것만으로 비교적 안전하게 백업이 된다. 만약 당신의 아이디나 웹사이트 등을 이름으로 하는 경로 자체가 민감한 정보라면, 이를 다시 암호화된 tarball로 압축해서 백업할 수도 있다.

$ tar -cz .password-store \
    | gpg --sign --encrypt -r 0x77BB8872 \
    > password-store-backup.tar.gz.gpg

이 tarball은 비슷한 방법으로 다시 복구시킬 수 있다.

$ gpg --decrypt \
    < password-store-backup.tar.gz.gpg \
    | tar -xz