웹 브라우저 포렌식 (IE/MSEdge, Chrome, Firefox)
2022 CodeEngn Conference 18
웹 브라우저 포렌식 (IE/MSEdge, Chrome, Firefox)
https://www.youtube.com/watch?v=qyokaHpWSD0
엔드포인트 공격은 어디에서 주로 시작될까?
피싱 | 이메일, 문자, SNS 등을 통한 소셜 엔지니어링 공격 인증을 유도하여 계정과 암호를 탈취하거나 트로이 목마 설치 |
Drive-By Compromise | 취약한 상태에서 악성 웹사이트 방문으로 감염 |
원격 서비스 | VPN, Citrix, 팀뷰어, VNC 등 외부에 노출된 다양한 원격 제어 서비스를 통해 침투 다크웹에서 유출 정보를 구매하거나 일부 자산 공격 성공 후 계정과 암호를 얻어내어 활용 |
이동식 장치 | 윈도우 10 이전의 구형 시스템은 USB 연결 후 자동 실행 등을 통해 감염될 수 있음 |
공급망 공격 | 상대적으로 취약한 공급망 체계를 공격하여 개발 도구나 패키지에 악성코드를 삽입할 수 있음 |
웹 브라우저 아티팩트
ESE 데이터베이스
- Window app에서 흔히 사용되는 스토리지 엔진
ESE DB 구조
페이지 0 | 파일 헤더 |
페이지 1 | 쉐도우 파일헤더. 페이지 0과 동일한 데이터가 들어간다. 페이지 0에서 크래시 등 불완전하게 기록이 되는 상황이 벌어졌을 때, 페이지 1의 데이터를 덮어씌워서 복원한다. |
페이지 2 | 첫 번재 페이지 |
... | ... |
다른 스토리지 엔진들: 페이지 헤더를 명시적으로 구분한다. 데이터를 뒤에서부터 앞으로 채우는 경우가 흔하다.
태그 0 | 페이지 헤더 |
태그 1 | 첫 번째 레코드 |
... | ... |
다른 스토리지 엔진들: 포인터들이 상단에 있다.
... | ... |
태그 1 포인터 | 태그 1을 가리킴 |
태그 0 포인터 | 태그 0을 가리킴 |
카탈로그
- 페이지 4에 존재
- 모든 메타데이터들이 관리된다.
- 테이블, 인덱스, 컬럼 정의 등 모든 객체에 대한 메타정보를 관리한다.
- FDP(Father Data Page): 테이블별 최상위 페이지 번호
- Type: 컬럼에 대한 정의
파일 헤더
- 인터넷 익스플로러는 WebCacheVo1.dat 파일에 모든 히스토리가 저장되어 있다.
- 평상시에는 lock이 되어 있는 상태. 별도의 잠금을 해제하고 파일을 복사하는 방법을 써야 한다.
- ESE DB 파일인지 확인하기 위해서 시그니처를 확인한다.
- 오프셋을 계산하려면 웹페이지 크기에 5를 곱해야하기 때문에, 페이지 크기를 확인해야 한다.
페이지 헤더
- 페이지 태그 수: 현재 페이지에 몇 개의 아이템이 존재하는지 나타내는 정보. 정보를 DB에서 탐색하기 위해 중요한 부분.
- 페이지 플래그: 비트를 사용.
레코드
- 고정 길이 컬럼 배열: 정수 타입 같은 것은 대부분 길이를 고정으로 쓸 수 있다.
- 가변 길이 컬럼 배열: 문자열 같은 경우는 가변 길이로 설정할 수밖에 없다.
- 태그 배열: 페이지 크기를 넘어가는 긴 텍스트들을 오버플로우 페이지에 기록하고, 오버플로우 페이지에 대한 포인터를 기록한다.
컬럼 타입
- 고정 길이 컬럼은 번호가 매겨져 있다.
긴 값
- type 4번이라는 것이 long value라는 의미.
ESE DB - IE History 메타데이터 조회
- 인터넷 익스플로러는 containers 테이블에 익스플로러 관련 메타데이터를 저장하고 있다. 사이트 방문 기록, 다운로드 기록 등.
- container id를 확인하고, 'container_숫자'를 입력하면 원하는 사이트로 방문 기록을 확인할 수 있다.
- 매번 이렇게 하는 것은 귀찮기 때문에, 익스플로러 관련 명령어를 만들어 놨다. (ie-downloads)
SQLITE: 초소형 SQL 데이터베이스 엔진
Dwayne Richard Hipp
- SQLITE DB 개발자
- 파서 생성기 직접 개발(Lemon)
- 형상관리 도구 직접 개발(Fossil)
- 프로젝트 관리 도구 직접 개발(CVSTrac)
SQLite 파일 구조
- 페이지 단위로 파일이 나뉘어져 있다.
- ESE DB에 비해 compact한 구조
- 셀 포인터는 앞에서부터 뒤로, 셀 데이터는 뒤에서부터 앞으로
SQLite 페이지 헤더
- 오른쪽 페이지 번호: 중간에 있는 인테리어 노드에만 존재하는 바이트
- 타입: 테이블의 인테리어 노드(0x05), 테이블의 리프 노드(0x0d), 인덱스의 인테리어 노드(0x02), 인덱스의 리프 노드(0x0a) 중 무엇인지 구분
SQLite 셀 구조
- Variable Integer Encoding: 왼쪽 첫 번째 수가 1이면 다음 데이터가 존재, 0이면 더 존재하지 않음을 나타낸다.
SQLite 오버플로우 처리
- 페이지 크기보다 큰 데이터는 대부분 오버플로우 페이지에 기록하고, 현재 페이지에는 데이터 앞부분과 오버플로우 페이지 번호를 기록한다.
- 얼마만큼을 인페이지에, 얼마만큼을 오버플로우 페이지에 기록하는지 수식을 통해 계산하도록 되어있다.
- 모든 테이블 키는 정수형이므로 절대 오버플로우되지 않는다.
SQLite 스키마 정의
- 1 페이지부터 순회하면 스키마 레코드를 조회할 수 있다.
컬럼 | 설명 |
type | table or index |
name | table name or index name |
table_name | table name |
root_page | root page number |
sql | table or index에 대한 DDL |