URL Redirection, URL Forwarding 이라고도 부르는 이 취약점(?) 공격 방법은 사용자로 하여금 의도하지 않은 페이지로 이동시키는 목적을 가지는 공격 방법입니다.
대게 로그인, 로그아웃부터 각종 페이지 이동 파라미터 등 XSS 와 비슷하게 웹 침투 시 많이 찾아낼 수 있는 취약점입니다. 페이지를 이동하여 악성코드 배포지나 Exploit 가 삽입된 페이지 등으로 강제 이동시켜 이후에 공격을 성공시키기 위한 발판으로 사용할 수 있습니다.
간단하게 원리 설명하고 바로 우회 패턴으로 넘어갈까 합니다.
URL Redirection 의 원리와 대응 방안
원리 자체는 매우 단순합니다.
페이지를 이동 시키는 요청에 대해 위조된 url 값을 넘겨주어 피해자가 다른 사이트로 넘어가도록 유도합니다.
Location 헤더나, javascript(document.location.href) 등 에 남을 때 해당 부분에 악성 URL 주소가 들어가게 되고, 사용자는 바로 해당 주소로 넘어가게 됩니다.
대응 방법은 아주 간단합니다. 파라미터에 대한 검증 절차 만으로도 쉽게 막아낼 수 있습니다. 서비스에서 허용하는 페이지에 대해서만 Redirection 시키도록 하거나 이전 페이지(Referer 헤더)에 대한 검증으로 해결이 가능합니다.
URL Redirection 우회 기법
URL Redirection 의 취약점 설명이나 대응 방안을 소개하기 위해 이 글은 적은 것은 아닙니다. 그래서 소개랑 대응을 굉장히 간단하게 적었지요. 제가 여러가지 테스트를 하다 보니, 간단하고 쉽게 우회되는 Case가 좀 많았습니다.
분명 취약 페이지들은 Redirection에 대한 검증을 하는 페이지이지만, 간단한 방법으로 우회가 가능합니다.
1. 하위 도메인(cname)을 이용한 우회 기법
대체로 redirection 에 대해 제어할 수 있는 파라미터에 대해 문자열로 비교를 하게 되는데 이 점을 이용한 방법입니다.
간단하게 redirection 이 가능한 php 코드를 가지고 설명하도록 하겠습니다.
test.php
<?
$url = $_GET['url'];
echo "<script>document.location.href='".$url.'";</script>"
?>
이라고 하면 우리는 get 요청을 통해 url 파라미터에 원래 기능과는 다른 url 주소를 호출하여 URL Redirection 이나 XSS 취약점에 사용할 수 있습니다.
original code: /test.php?url=this_site_page
여기서 개발자는 filter라는 함수를 만들어서 url에 대한 검증을 하게 되지요.
<?
$url = $_GET['url'];
$url = filter($url); // filter 함수는 문자열을 비교하여 white list 기반 필터링을 수행
// url 값이 this_site_page 인지 확인
echo "<script>document.location.href='".$url.'";</script>"
?>
이 때 공격자는 아래와 같이 우회할 수 있습니다.
Attack code: /test.php?url=this_site_page.malwareurl
이러면
this_site_page 의 상단 도메인으로 악의적인 url이 들어가고, php는 this_site_page 주소만 확인하여 필터링하지 않습니다. 이러한 방법으로 URL에 대해 검증하는 페이지를 우회할 수 있습니다.
2. 위조 파라미터를 통한 우회 기법
1번에서 소개한 cname 을 통한 조치하거나, 일반적으로 정확하게 검증되지 않은 사이트에 유효한 방법입니다. 개인적인 생각으로는 1번보다 활용성이 더 좋다고 봅니다.
이번 방법도 아주 간단합니다. 바로 필터링하는 부분을 파라미터로 넘기는 방법입니다. 이러한 방법을 사용할 경우 도메인을 검증하기 위해 맨 끝 부분부터 처리하는 경우 우회가 가능하고, 일반적인 문자열 비교 방법도 우회가 가능합니다.
위에랑 동일한 예시로 진행하겠습니다.
<?
$url = $_GET['url'];
$url = filter($url); // filter 함수는 문자열을 비교하여 white list 기반 필터링을 수행
// url 값이 this_site_page 인지 확인 / this_site_page 주소가 맨 끝에 있는지 확인
echo "<script>document.location.href='".$url.'";</script>"
?>
이런식으로 this_site_page 주소가 맨 끝에 있는지 확인하는 필터링이 있다고 가정합니다. 필터링을 패스하기 위해 white list 에 있는 페이지를 맨끝에 위치하고, 원하는 도메인으로 넘기기 위해 this_site_page 주소를 파라미터로 넘깁니다.
Attack code: /test.php?url=malwareurl/?.this_site_page
이러한 방법으로 요청 시 php는 마지막에 있는 this_site_page만 보고 정상 site 로 확인하여 Redirection 시키게 됩니다.
우회 기법에 대한 대응 사실 위에 우회 방법은 굉장히 간단하지만 대응하기는 약간 까다로운 면이 있습니다.
White List 기반 필터링을 적용하되 유의 사항이 존재합니다.
-
정규표현식이나, 문자열 비교를 통해 정확한 Domain 주소 확인 말로는 한줄로 적어지나, 실제로 바로 만들려고 하면 시간이 좀 걸릴 수 있는 부분입니다. 정확하게 실제 도메인이 의미하는 부분만 뽑아내어 비교하는 방법으로 해결이 가능합니다.
-
입력값된 도메인에 대해 IP주소를 확인합니다. 정규표현식/문자열 비교에 비해 구현은 단순하지만, 실제로 서버에 어느정도 무리가 생길지 모르겠네요.
※ 정확하게 도메인에 대한 검증이 필요
작성하다보니 생각보다 양이 많아졌습니다. 이 내용은 PDF로 정리하면 좋을거 같으니, 틈틈히 밤마다 작성하여 어디든 공유해보도록 하겠습니다. 감사합니다 :)