보안 점검을 받게 되어 표준 점검 항목을 미리 우리 코드에 대 봤다. 몰라서 안 한 것도 있고 알면서 미뤄 둔 것도 있었다.
Table of contents
Open Table of contents
화면에만 있던 권한 확인
목록 조회에는 자기 계정 조건이 들어가는데 상세 조회는 식별자만 받고 있었다. 화면에서 자기 것만 보이니 다른 식별자를 알 방법이 없다고 전제한 구조였다.
식별자가 순서대로라 옆 번호를 넣으면 그대로 열렸다. 조회할 때마다 그것이 이 사용자의 것인지 조건에 넣게 고쳤고 한 곳이 아니라 전부 찾아 고치는 데 시간이 걸렸다.
순서대로인 번호가 새는 것
순서대로인 식별자는 두 가지를 흘린다. 옆 번호가 존재한다는 것을 알려 주고 지금 번호로 전체 규모를 짐작하게 한다.
그래서 내부 식별자는 그대로 두고 밖으로 나가는 값만 다른 형태로 만들었다. 처음에는 단순한 규칙으로 바꿨는데 몇 개를 비교하면 규칙이 드러나서 다시 만들었다.
로그에 전체를 찍으면
로그를 훑어보니 비밀번호는 가려져 있는데 카드번호와 토큰이 그대로 남아 있었다. 응답 전체를 찍는 코드가 여기저기 있었고 그 안에 무엇이 들어 있는지는 안 보고 있었다.
가려야 할 항목 목록을 만들어 나가기 전에 지우게 했다. 근본은 전체를 찍지 않는 것인데 전체를 찍으면 나중에 필드가 추가돼도 모른 채 함께 나간다.
친절한 오류가 정보를 준다
로그인 실패 메시지가 아이디가 없는 경우와 비밀번호가 틀린 경우로 나뉘어 있었다. 친절한 안내로 만든 것인데 그것으로 어떤 아이디가 가입돼 있는지를 가릴 수 있다.
하나로 합치면 사용자에게는 불친절해지지만 그 구분이 밖으로 나가지 않으므로 받아들일 만한 맞바꿈이었다. 시도 횟수도 세지 않고 있어서 계속 시도할 수 있는 상태였다.
잠그는 것 자체가 공격이 되는 자리
횟수를 세어 일정 이상이면 잠그게 하려니 다른 문제가 보였다. 남의 아이디로 일부러 틀려서 잠그면 그 사람이 못 쓰게 된다.
그래서 계정 단위만이 아니라 요청이 오는 곳 단위로도 함께 셌다. 완전한 답은 아니라고 보고 그 사실을 함께 적었는데 의존성 취약점 확인과 설정 파일의 접속 정보 처리는 아직 못 한 것으로 남겼다.
정리
- 화면에서 안 보인다고 접근이 막힌 것이 아니다
- 조회할 때마다 그것이 이 사용자의 것인지 조건에 넣는다
- 순서대로인 식별자는 존재 여부와 규모를 함께 흘린다
- 밖으로 나가는 값만 바꾸되 규칙이 드러나지 않게 한다
- 로그에 응답 전체를 찍으면 새 필드가 모른 채 함께 나간다
- 실패 메시지를 나누면 그 구분 자체가 정보가 된다
- 시도 횟수를 세되 잠그는 것이 공격이 되는 경우를 함께 본다
- 못 한 항목을 남겨서 다음에 무엇을 할지 남긴다