13번째로 푼 문제이다. :)
인젝션 문제이다.

문제 이름! SimpleBoard




(SimpleBoard)



문제 페이지이다.



(문제 페이지)



게시판 형식의 페이지이다.

소스코드를 확인 해보자!




(소스코드)



소스코드를 보니 완전한 소스코드가 아니라 클래스 부분만 따로 때어낸 코드를 주었다.

코드 안에서는 우리가 공략할 수 있는 쿼리문을 보여준다.
여기에 사용된 쿼리는 update와 select 쿼리가 사용되었다. update 쿼리는 조회수 정보를 저장할 때 사용되었고 select 쿼리는 게시글을 클릭하였을 때 게시물을 보여주기 위해 사용되었다.

그렇다면 이러한 쿼리들은 어떤 인자를 받아들여 쿼리를 실행할까?
게시글 아무거나 클릭해보았다.



(게시글 클릭)



클릭해보니 GET방식으로 idx를 넘겨주고 있다.

또 소스코드를 보면 idx를 통해 select를 하고 update를 한다.
정확히 GET으로 받은 idx를 사용하는지는 안나왔지만 클래스 코드를 보고 유추하자면 그렇다.

그렇다면 idx 변수에 injection을 담아 보내보자!
4 and 1 을 보내본다.



(4 and 1)



4번 글이 실행되었다.
이와 비교해서
4 and 0
을 Injection해보았다.




(4 and 0)



화면에 아무것도 나오지 않는다.
즉 이말은 4 and 0의 쿼리가 잘 전달되어 게시글을 가져오지 못했다는 것이다.

그렇다면 제일먼저 이 테이블의 컬럼수를 알아보기 위해
order by를 이용할 것이다.




(order by 1)



쿼리 에러

여기서 당황했지만 코드를 다시 잘 살펴보게 되는 계기가 되었다.




(소스코드)



여기서 idx값이 전달되면 쿼리가 2개가 실행되는데
update 쿼리를 잘보면 우리가 보낸 4 and 1 order by 1을 하게 되면 여기서 에러가 난다는 것을 알 수 있다. 즉 update 쿼리가 실행되지 않게 해야하는데 쿠키값으로 view를 관리하는 것을 볼 수 있다.
이 값에 봤다고 설정이 되있다면 update쿼리는 실행되지 않는다.

매번 쿠키를 설정해서 보내기 귀찮으므로 파이썬을 이용해 코드를 작성해보겠다.



(작성한 코드)



이 코드를 보면 4 or 1 order by 1 를 보낸다.



(결과)



결과를 보니 잘 나오는 듯했다.
하지만 잘나온것은 아니다 왜냐! 4번글이 출력되었기 때문에
정상적이라면 1번글이 나왔어야한다.

이유를 헤메다 보니 쿠키에 저장되는 값을 url 인코딩으로 해줘야한다.!
그렇기에 url 인코딩해서 보내주면



(url 인코딩 injection)



(실행결과)



실행 결과를 보면 1번 글이 출력된 것을 확인 할 수 있다.

이제 order by를 이용해 컬럼의 수를 찾아보겠다.



(order by 5 injection)




(쿼리 에러)



1,2,3 이렇게 늘려가다보니 5에서 에러가 났다.
컬럼의 수는 4개라는 것을 알 수 있었다.

이젠 4개의 컬럼이 맞는지 union select 를 이용해 확인해 보겠다.
원래 안에 글의 개수가 4개이므로 출력해줘야하는 글의 위치는 4 (0부터시작하므로)
limit 4,1 을 붙여주었다.




(확인 injection)




(실행결과)



실행결과를 보니 1,2,3,4 가 출력되는 것을 확인 할 수 있었다.

이제 테이블 이름을 알아야했다.
테이블 이름을 알기위해
select table_name,2,3,4 from information_schema.tables 를 이용할 것이다.



(테이블 이름 injection)



(실행결과)



실행 결과를 보니 CHARACTER_SETS이 나왔다.
나는 이게 지금 내가 검색하고 있는 테이블 이름인줄 착각했었다.. 하지만 여러 테이블 이름 중 하나였다.

즉 테이블 이름을 쭉 전부 검색해서 확인할 필요가 있었다.



(테이블 이름 injection)




(실행결과)



실행결과 쭉 보니 의심갈만한 테이블 이름이 있었다.
SimpleBoard 와 README 였다.

SimpleBoard을 살펴보니 우리가 문제 페이지에서 확인할 수 있는 페이지가 전부였다.

남은건 README!

하지만 컬럼 이름은 모르는데.. 컬럼이름을 찾을까 하다가
그래도 flag라는 컬럼이 있지 않겠어? 라는 심정으로 찍어봤는데



(flag injection)




(실행 결과)


flag가 정말 나왔다...
문제해결..!! :)


'WarGame > 500 Project' 카테고리의 다른 글

(15/500) Wargame.kr - lonely guys  (0) 2017.04.18
(14/500) Wargame.kr - strcmp  (0) 2017.04.16
(12/500) Wargame.kr - tmitter  (0) 2017.04.15
(11/500) Wargame.kr - type confusion  (0) 2017.04.15
(10/500) Wargame.kr - md5 password  (0) 2017.04.14


12번째로 푼 문제이다!

tmitter


(tmitter)



아래는 문제 페이지이다.


(문제 페이지)



문제 페이지 보니 로그인하는 버튼과 회원가입하는 버튼이 있다.

회원가입 페이지에 들어가서 이것저것 해보다가 소스코드를 보니 힌트가 있었다.



(힌트)



개인적으로 나에게 이 힌트가 매우 컸다.
이곳저곳 쑤시지 않고 여기만 공략하면 됬기에!! ㅎㅎ

admin 으로 회원가입을 하라는 말이다.
그렇다면 해보자!



(거부)



admin 계정이 이미 있다고 나온다.
역시..

그렇다면 분명 select 쿼리가 날라가서 db를 검색하여 자료가 있으면 이미 존재한다고 나오는거겠지??
라는 생각이 들었다.

흠 우선 admin' # 을 넣어 오류를 내보자!



(sql injection)



응??
' 앞에 역슬래쉬가 붙었다.
이 워게임 사이트 앞에서 php 코드를 살펴보니 그 injection 방지용으로 어떤 함수를 잘 쓰던데 그거 썻나보다. ' 앞에 이스케이프 된다.

그렇다면 널바이트는 어떻게 될까? 널바이트는 포스트로 전달 못하니
버프슈트를 이용해서 널바이트를 추가해서 보내보자!



(널바이트 삽입)



결과는...




(결과)



널바이트앞에도 이스케이프 문자가 붙는다.

역시..! 그 mysql_real_escape_string()을 쓰는거 같다.
아그러면 or나 이런거도 붙을텐데... 고민이 들었다.

일단 이 함수의 우회법은 안다.
바로 싱글 쿼터 앞에%bf를 넣어주면 %bf가 이스케이프 문자와 합쳐져서 싱글쿼터가 살아남는다.
그 뒤에 && 0 을 추가시켜주어 select 문에 아무것도 안나오게하고
그래서 회원가입이 되게 하는게 나의 전략이다.



(sql injection)



실행결과 회원가입이 되었다.!

정한 비밀번호로 로그인을 해보면




(로그인)



로그인이 되고 flag를 찾을 수 있다.!



(문제 해결)

'WarGame > 500 Project' 카테고리의 다른 글

(14/500) Wargame.kr - strcmp  (0) 2017.04.16
(13/500) Wargame.kr - SimpleBoard  (0) 2017.04.16
(11/500) Wargame.kr - type confusion  (0) 2017.04.15
(10/500) Wargame.kr - md5 password  (0) 2017.04.14
(9/500) Wargame.kr - md5_compare  (0) 2017.04.13




@23번문제
블라인드 인젝션으로 Suninatas에 있는 웹카테고리의 마지막 문제이다.
난이도가 있었지만, 보통의 블라인드 인젝션이었다.
MsSQL DB라는 것을 감안해야하고 곳곳의 어려운부분이 있기는 하다.




(23번 문제)



(문제 화면)



문제화면을 보니 필터링하고 있는 키워드 중에 admin 단어가 보인다.

블라인드 인젝션으로 이번 문제는 admin의 비밀번호를 찾는 것이 목적인데,
admin을 필터링 했다니.

일단 사용할 수 있는 키워드와 주석, numeric/string인지 여부를 확인하기 위해
인젝션을 시도하였다.
그 중 성공한 쿼리를 통해서 알 수 있는 내용은 다음과 같았다.



(성공 쿼리)



id 부분은 string으로 들어가고 있고 or, =, -- 기호를 사용할 수 있다.

또 이 문제에서 조금 힘들었던 부분이 길이제한인데..
예를들어 다음과 같이 길이가 조금 길다 싶으면 No hack이라고 떴다.
처음에는 어떤 단어를 필터링 하고 있는 줄 알았는데
키워드가 아닌 길이에서 필터링을 하고 있었다.



(필터링 된 모습)



최대 몇글자까지인지 확인해볼 필요가 있다.




(길이 확인)



최대 길이를 확인해보니 30 글자였고
30글자를 넘어가면 No hack이라고 떴다.

우리는 30글자 이내의 쿼리문을 만들어야한다.

그리고 또 우리가 해야할 일 중 하나는
admin의 행을 select할 수 있도록 해야하는데
처음에는 id에서 guest가 아닌 행을 찾도록해서 admin 계정의 행을 select 하는데 성공했다.




(admin select 성공)



하지만 이렇게 할 경우 블라인드 인젝션을 하려면 뒤에 긴 쿼리가 붙어야하는데
한계가 있었다..
즉, admin을 우회해서 입력할 수 있어야했다.

구글에 문자열 필터링을 치니 가장 먼저 나온것이
쿼터로 끊어주는 것이었다.
ex 'admin = 'adm'+'in'

이런 방법이 적용되는지 확인해 보았다.



(인젝션)



admin 행을 select 하는데 성공했다. :)
이제 블라인드 인젝션을 해야하는데 평소와 같이 나는 이렇게 입력했다.



(인젝션)



결과는 당연히 False였다. MsSQL에서는 mid함수를 지원하지 않는다...
그렇기에 내게 남은건 left 함수밖에 없었는데(substring을 필터링하고있어서...)
left를 쓰면 비밀번호 길이가 12글자인데(비밀번호 길이를 구하는 과정은 사진찍지 못했다.!)
30글자의 쿼리를 넘지않을까 걱정이 들었다.
하지만 우리에겐 right함수도 있으므로 막히면 right로 교체해서 반씩 알아내도 되겠다는 생각이 들었다.
첫글자는 파이썬으로 V였다.



(인젝션)



이런식으로 파이썬 코드를 작성하여 한글자씩 찾았다.
(12글자라서 금방 끝났다.)




(작성 코드)





(결과)



첫번째 글자는 V였고
두번째 쿼리는 admin'+'n'and left(pw,2)='V + chr(i)'-- 을 이용하여 찾았다.




(2번째 글자)




(결과)



결과는 3이었고
이제부터 No hack이 뜨기 시작했다.
그리하여 쿼리문을
'or left(pw,3)='V3 + chr(i)'-- 로 바꾸어서 찾았다.



(3번째 글자)




(결과)



이런 식으로 한글자씩 찾을 수 있었고

마지막에 admin으로 로그인해본 결과 비밀번호가 일치했다.



(문제 해결)



이제 이 비밀번호를 인증키에 입력해주면 끝이다. :)


'WarGame > SuNiNaTaS' 카테고리의 다른 글

SuNiNaTaS : Challenge WEB 22  (0) 2017.03.29
SuNiNaTaS : Challenge WEB 8  (0) 2017.03.29
SuNiNaTaS : Challenge WEB 6  (0) 2017.03.28
SuNiNaTaS : Challenge WEB 5  (0) 2017.03.27
SuNiNaTaS : Challenge WEB 4  (2) 2017.03.23


@22번 문제
Blind Injection 문제로 자신있었던 문제이다. :)



(22번 문제)



(문제 화면)



문제 화면을 보면 필터링 되고있는 단어들을 보여주고 있다.
먼저 id에 입력되는 값이 numeric인지 string인지 체크하기 위하여
주석을 사용해보았다.
(여기서 이 사이트가 내가 풀던 사이트랑 조금 다른데? 라고 느꼈던 부분이 있는데
 DB를 MsSQL을 쓰는 것 같았다.)
MySQL에서 #이 주석으로 먹혔는데 여기서는 #이 주석으로 먹히지 않았다.
그래서 주석 -- 를 사용했다. 다행히 --은 필터링 하지 않았다.



(주석 이용)



주석만 사용했을 때 에러가 났고 이로써 numeric이 아니라 string인 걸 확인 할 수 있었다.

즉 쿼터로 닫아주고 다시 -- 주석처리를 해주니



(OK admin)



admin으로 로그인이 되었다.
이제 여기서 admin의 비밀번호를 찾으면 되는데
여기서 DB가 MsSQL이라는 것에 확신이 간 계기가 있었다.
MySQL에서 사용하던 함수들이 먹히지 않는 것들도 있다는 것이다.
예를들어 아래 Length() 함수가 MsSQL에서는 Len()으로 사용되는데 이러한 차이가 있었고
다시 찾아보면서 Injection하느라 조금 시간이 걸렸다.

DB별로 미묘한 차이들이 있으므로 정리해 둘 필요가 있는것 같다.

다시 문제로 돌아와서 먼저 비밀번호의 길이부터 구했다.



(Injection)



확인해보니 9보다 크고..



(Injection)



길이는 10글자였다.
이제 한글자씩 찾으면 된다.

물론 손으로 찾기는 힘드니 파이썬을 이용했다.
ascii나 hex, ord 가 가능했다면 손으로도 금방 찾긴했을테지만
전부 필터링 되어있으니
직접 하나하나 체크하는 수 밖에 없다.



(코드 작성)



코드 작성 후
돌려준다. :)





(문제 해결)



이렇게 문제를 해결했다. :)



'WarGame > SuNiNaTaS' 카테고리의 다른 글

SuNiNaTaS : Challenge WEB 23  (0) 2017.03.30
SuNiNaTaS : Challenge WEB 8  (0) 2017.03.29
SuNiNaTaS : Challenge WEB 6  (0) 2017.03.28
SuNiNaTaS : Challenge WEB 5  (0) 2017.03.27
SuNiNaTaS : Challenge WEB 4  (2) 2017.03.23

@6번문제

생각보다 오래걸렸다. 너무 쉽게봤는데(그렇다고 어려운문제는 아닌것 같다.)

시간이 걸리는 문제였다.



(6번 문제)




(문제 화면)



문제 화면을 보면
README 라는 3번 게시물은 패스워드를 입력해야 들어갈 수 있었고
나머지는 그냥 글 들이었다. (알고보니 힌트들, 아닌것도 있지만)

3번 비밀번호 입력하는 팝업창이 뜨고 친절하게 보내지는 쿼리도 보여준다.



(비밀번호 입력창)



Injection이라면 조금 자신있어서 신나게 풀었다.
먼저 입력이 string이다.
필터링 되는 단어를 확인해 본다.




(sql injection)





(결과)



결과를 보니 #이 필터링 되고 있었고 다른 주석으로 -- 을 사용했다.





(다른 주석 사용)




(노필터링)



필터링 되지 않고 쿼리가 날라갔다. 이제 주석은 --을 사용할 것이다.
보통 MySQL에서는 1이 참이라고 인식되던데 False가 나와
1=1(참)로 바꿔서 입력해주었다.




(=필터링)



= 이 필터링 되고있다..ㅎㅎ

=은 like, in 등으로 대체할 수 있다.
그 중 쉽게 like를 써보았다.



(like로 대체)






(문제 해결?)



문제가 해결되었다.

뭔가 싱거운 기분이 들었다. 이게뭐야

하지만 지금부터 시작이라는걸 알았다.
이 인증키를 답에 입력해보니...



(틀림)



틀린다고 나온다. 답이 아니다...
뭐야..

아까 비밀번호 인증 성공 후 아래와 같은 팝업창이 떳었는데..




(접근 제어)



이 팝업창을 무시했었는데 아무래도 여기에 문제가 있었나보다.

접근 권한을 어디서 체크하겠는가. Cookie 값 혹은 SesssionID로 체크하니까

현재 cookie를 살펴보았다.




(쿠키값)



세션아이디도 있고, 인증키?도 적혀있다.
세션아이디는 아무래도 아이디 관련이 있는 거 같고
auth%5Fkey가 지금 제어당하고 있는 값인거 같다.




(인증키 설정)



인증키를 설정해준다! 아까 받았던거로
그러니 당연하다듯이 실패...

여기서 인증키를 변환해주어야한다

게시물중에 참조하라는 게시물이 있는데 그 게시물에 인코더 사이트가 들어있다.
인증키를 Encode해서 입력하라는 뜻인거 같다.
종류는 모르고...




(Base64로 인코딩)






(인증키 설정)



Base64부터 시작하여 저기 있는 방법으로 모두 해보았다.
그 결과 안된다.
심지어 저기 없는 방식으로도 했다. 다른 Encoder사이트 참조
안된다.

이유를 잘보니 키 인증값이 자꾸 %3F로 재설정된다.
그니까 넘겨줄때마다 계속 인증키를 다시 설정해야하는 것이었다.

그래서 여기서.. 툴을 쓰기로 했다:)
버프슈트를 이용해 인증키 변조
그리고 처음부터 다시시작(Base64부터...)

모든 인코딩을 해서 해본 결과 하나가 되긴한다.. :)




(인증키 변조)



성공하니 README의 게시물이 열렸다.




(게시물 오픈)



키를 찾으세요! 라는 문제가있다.

소스코드에 있나 하고 소스코드를 열어보았다.




(문제?)



이상한 action이 있는 form을 발견했다. 키 힌트가 로마의 첫번째 황제?

Rome's First Emperor 를 그대로 인터넷에 검색했다.
이게 답맞나... 싶었지만



(정답)



정답이었다..
:)


'WarGame > SuNiNaTaS' 카테고리의 다른 글

SuNiNaTaS : Challenge WEB 22  (0) 2017.03.29
SuNiNaTaS : Challenge WEB 8  (0) 2017.03.29
SuNiNaTaS : Challenge WEB 5  (0) 2017.03.27
SuNiNaTaS : Challenge WEB 4  (2) 2017.03.23
SuNiNaTaS : Challenge WEB 3  (0) 2017.03.22


SQL Injection을 크게 두 종류로 본다면
Numeric Injection과 String Injection이 있다.

1) Numeric Injection
- SQL Injection 취약점이 존재하는 입력의 형태가 정수일 때의 Injection이다.
정수의 타입으로 입력하기 때문에
String과 달리 ' 작은 따옴표가 없다.
그래서 뒤에 추가적인 명령을 바로 입력하여 SQL Injection을 할 수 있다.
ex)
select * from news where no=1 union select * from news
* 띄어쓰기를 할 수 있어야 추가적인 명령을 할 수 있다.
(만약 코드 상에 trim()이나 공백을 지워주는 함수가 있다면 불가능하다..)


2) String Injection
- Injection 취약점이 존재하는 입력의 형태가 문자일 때의 Injection이다.
우리가 입력하는 것이 작은따옴표 ' 안으로 들어가기 때문에 Numeric Injection처럼 바로 명령을 이어붙이지는 못한다. 다만 ' 따옴표를 사용해 문자열을 잘라줄 수 있으면 된다.

예를들어 아래와 같이 where 조건 이 항상 참인 경우( 1인경우 )
전체 값을 불러오는 것을 확인 할 수 있다.



(where 참 경우)



이 것을 이용해 id에는 String이 들어가므로
아래와 같이 항상 참이도록 SQL Injection을 하면 전체 ID 정보를 가져올 수 있고
인증에 성공하게 된다. (우리가 인증과정을 해당 ID와 비밀번호가 조건에 맞는 데이터가 있다면 인증에 성공하게 만들었다.)
(사실 이 코드는 굉장히 효율적이지만 치명적인 SQL Injection 취약점이 있다. 위와같이)

그렇다면 아래와 같이 Injection을 해보겠다.



(SQL Injection)




결과...
성공하지 못했다.

SQL Log를 살펴보니.!



(SQL Log 확인)



우리가 입력한 ' (작은 따옴표) 앞에 \(역슬래쉬) 이스케이프 문자가 붙어진 것을 확인 할 수 있다.
그렇기에
우리가 입력한 작은 따옴표가 제 역할을 하지 못한 것이다.
이유는! 바로 우리가 전에 /etc/php.ini 설정 파일에서 magic_quotes_gpc 라는 설정을 해주었기 때문이다..!
이렇게 되면 String Injection은 난이도가 팍! 올라간다..!
지금 우리는 SQL Injection을 확인해보는 것이므로... ㅎㅎ
설정 해제 후 확인해보도록 하자! :)



(설정 해제)



그 후 같은 SQL Injection 모습이다.



(로그인 성공)



원리는
위에서 설명한것 과 같이 항상 참이 나오는 SQL 명령을 삽입하였다. 물론 뒷부분은 처리되지 않도록 주석처리 하였다 .(#을 이용해서)
그래서 ID와 비밀번호 데이터가 전부 가져와졌고 우리가 만든 페이지 코드에서 데이터가 있다면 인증에 통과하도록 했기 때문에 통과 되는 것이다.

그렇다면 아이디 부분이 아닌 비밀번호 부분도 마찬가지 String이므로 같은 공격을 할 수 있다.


(SQL Injection)



Log를 확인해보면 우리가 원하는 SQL 명령이 들어간 것을 확인해 볼 수 있다.
조금 다른건
비밀번호 입력한 것이 password() 괄호 안에 들어가므로
1' ) or 1#
이렇게 괄호를 닫아주는 센스?!



(Log 확인)



이렇게 하면
없는 ID로도 로그인이 가능하다.



(로그인 우회)



그렇다면 이제 난이도를 올려보자!
분명 위에 처럼 where를 사용하여 조건에 맞는 데이터가 있다면 인증하는 것도 굉장히 혁신적인 코드이지만 취약점이 있다...
이제 우리는 아이디와 비밀번호를 DB에서 확인하여 일치하면 인증을 하도록 난이도를 올리겠다.



(난이도 업 코드)



ID만 쿼리문에 들어가있다. ID만 검색한 후 그 데이터에서 비밀번호를 입력받은 비밀번호와 일치하는지에 따라 인증을 하는 코드이다.

과연 이것을 우회할 수 있을까?
생각보다 간단하다 :)

저 코드를 잘 보면 알 수 있게 된다.
전 글에서 우리가
select * from login union select 1,2 from login
이렇게 하면 1, 2 컬럼이 추가되어 나오는 것을 확인한 적이 있다.
(기억이 안난다면 지난 글 확인!)

이것을 이용하는 것이다.
코드를 보면 사용되는 쿼리문은
select * from login where user='id' 이다.
여기서 id 에다가 다른값을 넣어준 후 작은따옴표로 문자열을 닫고 union으로 추가해서 우리가 원하는 값이 나오도록 하는 것이다.
Ex)
select * from login where user='1' union select 1, 2 from login;
을 하게 되면 어떤 데이터가 받아와질까?
바로 user가 1인 데이터가 없으므로

user  |  pass
  1         2 

이런 데이터가 받아와지는 것이다. 코드를 보면 이럴 경우 pass의 값 2를 가져오게 되고
우리가 만약 비밀번호에 2를 입력한다면? => ?!?!

하지만 코드를 잘보라~
입력받은 비밀번호를 md5해서 비교하고 있다.
(사실 DB의 값을 바꿔놨다. password에 md5로 해쉬한 값을 넣어놨다.)

그렇다면 mysql 내장함수를 이용하여
select * from login where user='1' union select 1, md5(2) from login;
를 한다면
2가 아닌 md5로 해쉬한 2의 값이 나오게 되고
우리가 비밀번호에 2를 입력하면
모든 조건이 맞는 것이다.!
즉! 우회 성공!

확인해보겠다.
select * from login where user='1' union select 1, md5(2) from login; 이 나올수 있도록
1' union select 1, md5(2) from login# 을 넣어주고
비밀번호에 2를 입력해주었다.



(SQL Injection)



결과..



(우회 성공)




이처럼 SQL 에 취약한 코드가 있다면 안전한 인증을 사용해도 우회가 가능하다는
가능성을 보았다.!




DB의 정보를 확인하기 위해
지난 글에서 SQL Injection을 했다. 바로 Guessing(추측) 공격으로 말이다.

하지만 DB에 관한 지식? 정보를 알면 조금 더 정확하게(?) 정보를 꺼낼 수 있다.

우리가 지금 사용하는 MySQL에 관한 지식을 이해해보면서
이러한 가능성을 이해해보자 :)

MySQL에는 기본 DB가 있다. (우리가 만들지 않아도)
그 중 하나가 information_schema인데 이 DB에는 DB내의 모든 정보가 들어있다.
information_schema는 MySQL5 이상에서만 존재한다.
이 DB는 논리적인 DB로 수정이나 삭제가 불가능하다.

이 information_schema DB를 살펴보자!



(information_schema DB)



이 DB에 들어있는 테이블들을 확인해보면
DB 정보가 들어있는 테이블들을 확인 할 수 있다.
여기서 우리는 테이블 정보가 들어있는 tables 라는 테이블을 확인해보겠다.



(TABLES 테이블)



테이블 내용 중 몇가지만 명령문에 넣어 select 명령문을 사용해보겠다.



(TABLES 내용 확인)



그렇다면
다른 DB에서도 information_schema DB에 들어있는 정보를 SELECT해서 확인 할 수 있는지 확인해보겠다.



(다른 DB에서 SELECT)



에러가 난다.!
그런데 에러 내용을 보니 blind.columns 이 없다고 나온다. 즉 경로를 입력해줘야 한다는 뜻이다.


select 1, column_name, table_name from information_schema.columns;
이런식으로 명령을 내리면 다른 DB에서도 해당 DB의 테이블 정보를 확인 할 수 있다.
그렇다면 union명령으로 SQL Injection 해보겠다.
information_schema 정보를 가져올 수 있다면 다른 DB에 대한 정보를 이용해 여러가지 정보를 가져올 수 있기 때문에 중요한 것이다.



(SQL Injection)



명령
http://100.100.100.129/view.php?no=1 union select 1, column_name, table_name from information_schema.columns;



(실행 결과)



실행 결과를 보니 information_schema DB의 columns 테이블의 정보들 중 우리가 선택한 column_name, table_name 정보가 나오는 것을 확인 할 수 있다. 첫번째 컬럼은 화면에 출력 되지 않으므로 그냥 1로 한 것이다.
우리가 이 페이지를 만들 때 일부러 취약하게 만들기 위해 while문을 사용했었는데
난이도를 올려 while을 제거해보겠다.


(while 제거)



제거하면 기존의 페이지 모습과 같다.



(제거한 모습)





(거짓 Injection)





(참 Injection)



다만,
아까와 같이 SQL Injection 시 정보가 주르륵 전부 나오지 않고 하나만 나오기 때문에 그리고 제일 먼저 담겨오는 원래정보만 나오기 때문에 난이도가 올라간다.
즉 여기서 우리는 새로운 명령 문법을 배워야한다.
바로 limit 명령이다.
limit을 이용하면 select의 개수를 정할 수 있다.
* limit 을 이용하면 출력의 개수를 정해줄 수 있다.

또 출력을 시작할 행의 번호 또한 지정할 수 있다.
MySQL에서는 0번부터 시작한다.
mysql> select * from [Table] limit 시작, 갯수;



(사용 예시)



위 사용은 10번째 행부터 10개 까지만 가져오도록 하는 명령을 사용한 것이다.

이것을 이용하면 아까 우리 페이지는 한개의 행만 가져올 수 있으므로 개수는 1개로 지정하되
시작하는 행의 번호는 자유이므로 아래와 같이 명령을 하게되면 정보를 확인 할 수 있게 된다.



(테이블 정보 확인)



이를 이용해
http://100.100.100.129/view.php?no=1 union select 1,2,table_name from information_schema.tables limit 1,1
이렇게 url로 SQL Injection을 하면 아래와 같이 나온다.



(실행 결과)




(실행 결과2)



여기서 난이도를 더 올려보겠다.
만약 화면에 DB 정보가 안나온다면??..



(DB정보 출력 제거)



난이도를 올린 페이지 모습



(업그레이드 페이지 모습)




(참 Injection)





(거짓 Injection)



참과 거짓을 이용했을 때 화면에 문구가 나오느냐 안나오느냐 확인 할 수 있으므로
SQL Injection에 취약한 지는 체크할 수 있다.

하지만 DB정보가 출력되는 곳이 없는데 어떻게 정보를 확인할 수 있단 말인가...

이를 이해하기 위해 우리는 또다른 mysql 명령 문법을 알고 가는 것이 좋다.
substr 이라는 문법이다.
이 문법은 php에서도 사용된다.

바로 문자열을 분할하는 함수이다.
이 함수를 이용하면 아래와 같이 한글자를 확인 할 수 있다.



(substr 이용 확인)



위 화면은 information_schema DB에 있는 tables 라는 테이블에 테이블 이름 컬럼의 정보 중 첫번째 행의 데이터의 첫번째 글자를 확인한 것이다.

이를 우리는 웹에서 DB정보가 출력되는 것이 없기 때문에 참과 거짓을 이용하여 찾을 것이다.
그러기 위해 참과 거짓이 되게 비교를 해야하는데 물론 문자도 비교가 되지만 정확하게 하기 위하여
아스키코드를 비교하는 것이 좋다.



(아스키 코드 비교 화면)



이를 이용하여 아래와 같이 비교문장을 and 뒤에 추가하면 만약 참이되면
화면에 글자가 나올것이고(Welcome 어쩌구)
만약 거짓이면 and이기 때문에 화면에 아무 글자도 출력되지 않을 것이다.
바로 이것을 이용하여 찾는 것이다.



(SQL Injection)





(거짓 화면)



그렇다면 66이 아니니 67을 너보는 것이다.



(참 화면)



67일 때 글자가 나온것을 봐서
67이구나 즉 C라는 글자구나라고 생각할 수 있다.
이런 식으로
ascii(substr( (select table_name from information_schema.tables limit 1,1), 2,1)) = 66;
ascii(substr( (select table_name from information_schema.tables limit 1,1), 3,1)) = 66;
...
이렇게 한글자씩 찾는 것이다.

비교문이므로 크다, 작다 부등호로도 판별이 가능하다.



(부등호 사용)



이제 난이도를 더 올려보겠다.
화면에는 이제 Welcome이라는 글자 조차.. 아무 화면도 안뜬다...
이런 상황에서도 가능할까??



(출력 정보 없다.)





(페이지 모습)





(참 Injection)





(거짓 Injection)




참도,, 거짓도... 알아볼 수 없는 화면이다...
이럴 때는 일부러 특이 현상을 일으키는 것도 방법이다.
예를 들어 sleep명령이 있다.
and 뒤에 비교문(아까와 같이) 또 그 뒤에 sleep을 걸어주면
비교가 참일 경우 sleep이 발생되고
거짓일 경우 뒤의 명령을 실행할 필요가 없기 때문에 sleep이 나타나지 않는다.
즉 이걸 이용하면 아까와 같은 방법으로 한글자씩 알아낼 수 있다.




(참 Injection)




참일 경우 위와 같이 sleep이 발동되어 화면이 돌아가고 있는 모습을 볼 수 있다.

이렇듯 화면에 출력되는 정보가 없어도
확인이 힘들더라도
SQL Injection은 가능할 수 가 있다.
:)



저번 글 마지막에서
SQL 인젝션을 막아보았다.
바로 magic_quotes_gpc 설정을 통해서인데
한번 어떻게 막아지나 다시한번 확인해 보겠다.

게시글 내용을 sql injection test글로 수정하는 쿼리로 조작해서
url입력을 한다. 



(SQL Injection)



결과는 물론 실행되지 않았고
로그를 통해 어떤 SQL 명령이 전달되었는지 확인해보자



(로그 확인)



전달된 SQL 명령을 확인해보니 문자열 앞 ' 작은따옴표 앞에 \(역슬래쉬) 가 붙은 걸 확인 할 수 있다.

바로 escape 문자인데 문자열을 나타내는 ' 작은 따옴표의 역할을 벗어나 문자 따옴표 역할을 하게 한다. -> 그렇게 되어 뒷부분이 SQL 명령 문법에 오류로 처리가 되어 SQL 명령이 실행되지 않는 것이다.

이러한 필터링을 우회하는 방법이 있을까?
=> 이러한 필터링은 문자열이 입력되지 못하게 하는 것이다.

* 우회 방법
1) 필터링 되고 있는 문자에 대해서 다른 문자로 대체 가능한 문자를 찾는다.

2) 문자열을 표현하는 또 다른 방법을 이용하는 것이다.
-> mysqld의 내장함수를 이용하는 방법이 있다. (char함수 이용)

char() -> 아스키 코드를 바꿔주는 char 내장함수를 사용하면 ' , " 를 사용하지 않고도 문자열을 입력할 수 있다.

MySQL에서 적용이 되는지 확인해 보겠다.
먼저 char() 함수를 이용하여 문자열이 출력 가능할까?



(문자열 출력)



-> 문자열 출력이 가능하다.

'sql injection haha' 이라는 문자열이 출력 될 수 있도록
아스키코드표를 참고해서 적어준다.
SQL Injection에 사용될 url이다. 



(SQL Injection)



실행 후 로그를 확인해보았다.



(로그)



로그를 보니 우리가 원하는 대로 SQL 명령이 전달 된 것을 확인 할 수 있다.

공격이 잘 성공 됬다면 게시판의 모든 글이 sql injection haha로 바뀌었을 것이다.
뒤에 우리가 where 조건 절을 안주었기 때문에 모든 글에 적용 되었을 것이고
concat을 사용하지 않았기 때문에 글 전체가 바뀌었을 것이다.

확인해보면



(결과)




(결과)



모든 글이 우리가 입력한 문자열로 모두 바뀐 것을 확인 할 수 있다.

그렇다면 이 우회방법을 이용하여 스크립트도 추가할 수 있을까?



(추가할 스크립트)



추가할 스크립트를 아스키코드로 바꾸어 놓았다.

아까와 같이 하지만 우리는 이번에 전체 글이 아니라 19번 글만 적용시킬 것이다. 왜냐하면
전체글에서 팝업창이 뜨면 귀찮을거 같기 때문에...



(SQL Injection url)



실행해보니 19번 글을 클릭할 때 XSS 스크립트가 실행되었다.



(XSS 공격)



소스코드를 보니



(소스코드)



XSS 스크립트가 추가된 것을 확인 할 수 있다.

이렇게 SQL Injection은 XSS 공격에도 이용할 수 있을 만큼 강력한 취약점이다.

이번에 다뤄볼 내용은 Blind SQL Injection이다.

* Blind SQL Injection
-> 소스코드 없이 오직 페이지에 있는 코드 혹은 SQL 명령들의 결과로부터만 공격을 하는 것이다.
-> DB에 들어있는 데이터 중에서 블라인드 데이터, 화면에 보여지지 않는 데이터들을 노출시키는 공격이다.
지금 까지는 우리가 서버에 들어가서 소스코드를 분석하면서 취약점을 분석하였다.
하지만 이번에는 오직 웹 브라우저를 통해서 공격하는 것이다.

먼저 이 공격에 대해 이해하기 위해
Blind Injection에 아주아주 취약한 웹페이지를 만들어보고 그 페이지를 대상으로 공격을 해보겠다.

1) 테스트용 DB
 DB : blind
 table 3개가 필요하다.
 - news: no, title, news
 - fnews: no, title, news, bigo
 - anews : no, title



(DB 생성)




(테이블 생성)




(적절한 데이터 입력)



DB 생성, 테이블 생성, 적절한 데이터까지 몇개 입력해보았다.

이제 이 DB를 이용해 간단한 그리고 취약한 PHP 페이지를 만들것이다.



(PHP 페이지 코드)



웹 페이지에서 확인해보면
no변수를 GET 방식을 통해 전달받으면서 해당 no의 글을 화면에 보여주는 페이지이다.



(웹 페이지 모습)



취약점의 존재 확인방법 : 참 or 거짓을 이용한다.
 1) and 1=1 , and 'a'='a',  and 1  , true false 사용 가능, && 기호(url인코딩값) 사용 가능  (참 이용)
 2) and 1=2, and 0, and False,   (거짓 이용)
 3) or 1=1  ,  || 기호 사용 가능(url인코딩사용해야한다.)
 4) or 1=2
참일 경우 화면에 보여지지만, 거짓일 경우에는 화면에 보여지지 않을 것이다.




(참)




(거짓)



이러한 명령들을 로그에서도 확인해 볼 수 있다.



(로그)



혹은 no의 변수에 1 || 1  을 입력하게 되면
뒤에 1이 항상 참이기 때문에 no=1의 글만이 아닌 1을 포함해서 모든 글을 가져오게 된다.



(1=1 입력)



이렇듯
입력값 조작 을 통해 화면이 다르게 나오면 인젝션 취약점을 의심해 볼 수 있다.
=> 입력값에 의해 쿼리가 사용된다는 것을 의심해 볼 수 있다.

그렇다면 조작할 수 있는 것은 알겠는데
이로써 다른 데이터들을 보려고 한다면 no변수에 입력을 통해 추가적으로 다른 테이블을 검색할 수 있어야한다.
즉, 2개 이상의 쿼리문을 실행시킬 수 있어야한다.
어떻게?

1). ; 을 이용한 방법
; (세미콜론)을 이용하면 여러개의 명령을 동시에 실행 시킬 수 있다.



(두개의 명령 실행)



검색 결과가 2개가 나온 것을 확인 할 수 있다.

하지만 안타깝게도 이 방법은 현재 우리 코드에서 적용하지 못한다. 이유는...
우리가 mysql_query() 함수를 사용하는데 이는 단일 쿼리만 가능하도록 되있는 함수이기 때문이다..
다른데서는 가능할 수 도 있지만, 우리에게는 사용할 수 없다ㅜ

2). union 을 이용한 방법 (이거는 select에서만 사용 가능하다.)
union을 이용하면 추가적인 select 명령을 할 수 있다.



(union 사용)



사용 화면에 보다시피 한테이블에 합쳐져서 나온다.

그렇기 때문에 예상할 수 있는 오류가 있다.
만약 두 개의 쿼리에서 찾는 테이블의 컬럼의 수가 일치하지 않으면??



(에러 모습)



에러가 난다~
news는 컬럼이 3개 이기 때문에 fnews 테이블을 컬럼 3개만 맞춰서 select 명령을 실행 할 수 밖에 없다.
무조건 앞에 있는 테이블을 기준으로 컬럼을 맞춰야한다.



(컬럼 일치시키기)



그렇다면 anews 처럼 2개 밖에없으면??
즉, news 보다 더 적은 테이블을 검색한다면 어떨까?



(오류)



물론 오류난다..

이를 해결하기 위해서는 컬럼을 일치시키기위해 아무값이나 추가해서 컬럼을 추가한다.



(컬럼 일치시키기)



바로~ 이러한 특성을 이용하여
보이지 않는? 테이블의 컬럼의 수를 맞출 수 있다.
현재 우리는 우리가 테이블을 만들었기 때문에 컬럼의 수를 알고 있지만
Blind SQL Injection이다.

우리에게 주어진건 웹페이지 뿐이다.!
이 때 이 화면에 보여지는 테이블의 컬럼의 수 정보를 알아내는 것은
매우 중요하다.
왜냐하면 뒤에 union을 사용하여 추가적인 다른 테이블을 검색해볼것인데
union을 사용하려면 앞의 테이블의 컬럼 수와 일치시켜야하기 때문이다.!

그렇다면 현재 페이지의 DB 컬럼 수를 맞추기 부터 해보자!

* 컬럼의 개수를 아는 방법
컬럼 개수를 아는 방법은 여러가지가 있다.
1. 찍기. (다해보기)
-> 무식한 방법일 수 있지만 확실한 방법이다.

union select 1
union select 1, 2
union select 1, 2, 3
...
쭉 다 해본다.
그렇게 되서 화면에 내용이 나오게되면 바로 그 만큼의 개수가 존재 한다는 것이다.
원리는 위에서 union 할 때 앞의 컬럼의 수와 일치하는 컬럼의 수를 입력해야 된다는 것이다.



(컬럼 수 맞추기)



컬럼 수가 3개 이기 때문에 1, 2, 3 이렇게 3개의 값을 컬럼 정보에 넣었을 때 데이터가 보인다.


(그렇지 않은 경우)



그렇지 않은 경우 SQL 명령에서 오류가 나기때문에 화면에 아무 내용도 보이지 않게 된다.

2) order by 를 이용한 방법
-> 2진 탐색을 이용할 수 있는 방법이다.

select 에서 order by를 이용하면 컬럼의 정보로 정렬을 할 수 있다.



(사용 예시)



그런데 이걸 바로 숫자입력?으로도 정렬을 할 수 있다.



(order by 1)



이 방법의 원리는 이렇다.
=> orber by 10 으로 했는데 안나왔다. -> 컬럼이 10개보다 적다.
 => order by 2 로 했는데 나왔다. -> 컬럼이 2개보다 많다는 뜻이다.




(order by 방법)



이렇게 컬럼의 수를 맞추는 방법까지 알아보았다.

이제 다음 포스트 글에서는 Guessing을 이용해 DB 정보에 더 다가가는 방법에 대해
알아보겠다
:)




오늘은
제로보드의 SQL 취약점을 살펴볼 것이다.

그 중에서 PHP File Download 취약점을 살펴 볼 것이다.

지난 글에서 만들었던 게시판에서 글을 확인해 보면
다운로드 옆에 숫자가 보이는데
다운로드 횟수를 보여준다.



(다운로드 횟수)



바로 이 횟수가 DB에 저장된 값 중 하나인데
이 페이지의 소스코드를 분석해보자

다운로드를 클릭하면 download.php 파일로 이동하는 것을 확인 할 수 있다.



(download.php 파일 이동)



download.php?id=gogo_test&page=1&page_num=20&category=&sn=off&ss=off&sc=off&keyword

=&prev_no=&select_arrange=headnum&desc=asc&no=19&filenum=1
코드를 보면 download.php 파일로 GET방식으로 변수들의 값을 가져가고 있는 것을 확인 할 수 있다.

그렇다면 download.php 파일을 확인해보자.



(download.php 파일)



소스 코드를 보면 44번 행에
mysql_query를 볼 수 있다.



(SQL 구문)



mysql_query("update $t_board"."_$id set douwnload".$filenum."=download".$filenum."+1 where no='$no'");
이 구문인데 실행될 떄 어떤 SQL이 만들어져서 보내지는지 확인해 보겠다.
먼저 $t_board 변수인데
download.php 페이지에서는 이 변수를 정의하고 있지 않다.
대신
이 페이지의 위 쪽에 코드를 보면
require "lib.php";  에서
즉 lib.php에서 이 변수를 정의하고 있는 것을 확인 할 수 있었다.



(lib.php 에서 정의)



확인한 결과
lib.php 39번라인에서 $t_board = "zetyx_board";로 정의 되어있었다.

또 나머지 변수는 GET 방식에서 넘어오는 변수들인 것을 확인 할 수 있다.
$id=gogo_test
 $filenum=1
 $no=19

즉, 이 값들을 토대로 해서
어떤 쿼리가 전송되는지 조합해보면
update zetyx_board_gogo_test set download1=download1+1 where no='19';
이러한 쿼리가 만들어져서 보내지는 것을 확인 할 수 있다.

실제로 이런 쿼리가 만들어지는지 확인해보자

먼저
SQL 로그를 기록되게 하기위해서 실행중인 SQL을 끄고 다시 실행하도록 하자.



(sql 종료)



종료 후 옵션을 걸어서 실행해 줄 것이다.

#> mysqld_safe --log=query.log &
로 실행하게 되면
로그가 기록되게 된다.



(로그 기록 실행)



기록되는 로그의 위치는
/var/lib/mysql 에 있는
query.log 파일이다.



(로그 파일 확인)



로그 파일을 열어둔채 다시 다운로드를 클릭하면
아래와 같이 로그가 기록되는 것을 확인 할 수 있다.



(로그 확인)



로그를 보면 우리가 예상했던 update 구문이 정확히 일치한다는 것을 볼 수 있다.
우리의 생각이 맞았던 것이다.

자 그렇게되면
우리가 조작할 수 있는 값은 3개
이 3개로 SQL구문을 Injection 할 수 있다는 것이다.

예를 들어 id변수를 hello로 바꿀 수 있다.



(SQL Injection)




(결과 화면)




그 결과 hello라는 게시판이 없어서 이런 페이지가 나왔고
아무 일이 이러나지 않았다.

두번 째로 no변수를 1로 바꾸어 보았다.




(no 변조)




no 1의 게시 다운로드1 의 횟수가 1 추가되었는지 확인해보자

mysql에 들어가서 아래와 같이 확인해본다.



(확인)



(1 추가)



확인해본 결과 1이 증가했다는 것을 볼 수 있다.

그렇다면 마지막으로 filenum?
$filenum=1=100
으로 하면 어떻게 될까?
그렇게 되면
update zetyx_board_gogo_test set download1=100=download1=100+1 where no='19';
이 되게 되고 문법에 맞지 않아 실행이 되지 않는다.
하지만 이러한 변조는 아마 눈치 챘을 거라 생각한다.
바로 다운로드 횟수 100으로 바꿀 수 있다는 가능성이 있다는 것이다.



(다운로드 회수 100 조작)



하지만 뒤에 문법이 맞지 않는다는 것이 문제다.
그렇다면 뒷 부분을 주석처리할 수 있다면?
주석 : --, /* */, #
예를 들어
update zetyx_board_gogo_test set download1=100#=download1=100#+1 where no='19';
이렇게 되게 하기 위하여
filenum에다가 1=100# 을 넣는다면
뒷부분은 주석처리 되고 다운로드1의 횟수가 100이 되는 SQL 명령이 된다.



(SQL Injection)




(실행 결과)



실행 결과 로그를 확인해보니 #이 빠져있다..!
바로 URL에서 입력할 때 특수 문자는 URL Encoding이 되기 때문이다.

* URL encoding
 - URL에서 사용하는 특수문자
 - 공백: +, %20 (아스키 코드)
 - 문자에 해당하는 아스키코드 앞에 %를 붙여주면된다.
 # -> %23

그렇기 때문에 주석 처리를 위한 # 대신에 %23을 사용한다면?



(%23 사용)



결과 다운로드 수가 100으로 적용된 것을 볼 수 있다.



(100 적용)



그리고 뒤에 where 조건이 없었으므로 아마 모든 글의
다운로드1 횟수가 100으로 됬을 것이다.



(100으로 적용됨)



이 때 사용된 쿼리문을 로그에서 확인해보면



(쿼리 확인)



#이 아까처럼 사라지지 않고
남아서 주석처리 역할을 한것을 볼 수 있다.


그렇다면~?
이러한 SQL Injection을 이용해 XSS공격을 할 수 있을까?
예를들어 update구문을 이용해 게시글에 스크립트를 추가하도록 하는 것이다.
그렇게 되면 스크립트 차단을 해놨어도 우회할 수 있는 길이 생기게 된다.

먼저 게시글이 DB의 어떤 컬럼에 저장되는지 확인한다.



(게시글 내용)



확인해본 결과 게시글은 memo라는 컬럼에 데이터가 저장되는 것을 확인 할 수 있다.

우리는 그냥 update를 사용하면 원래 글 내용이 사라지므로
원래 글 뒷부분에 스크립트를 추가해보겠다.

이를 위해 concat이라는 함수가 있다.
바로 문자열을 연결해주는 함수이다.



(concat)



위 처럼 문자열을 연결해주는 역할을 한다.

우리는 이것을 이용하여
concat(memo, '스크립트') 를 사용할 것이다.

그렇게 되면 아래와 같은 url이 나온다.



(공격에 사용된 url)



실제 적용해보면
예상되는 쿼리는
update zetyx_board_gogo_test set download1=100, memo=concat(memo, '<script>alert(\'attack!!\') </script>')  #=download1=100#+1 where no='19';
이렇다.
게시글 뒷부분에 스크립트 코드가 추가되는 것이다.



(SQL Injection 실행)



실행 후 로그를 확인해보면



(로그 확인)



우리가 예상한 대로 SQL 명령이 전달 된 것을 확인 할 수 있다.

우리가 where 조건을 주지 않았기 때문에
모든 글에 스크립트가 들어가서


(XSS 공격)



XSS 공격 팝업 창이 뜰 것이다.

게시글의 코드를 확인해보면



(스크립트 코드 추가)



스크립트 코드가 추가된 것을 확인 할 수 있다.


간단하게 이러한 Injection을 막기 위해
magic_quotes_gpc 라는 설정을 켜둔다. GPC(Get, Post, Cookie)
하지만 5.4버전부터 이 설정이 사라져있다. (성능 때문에)

설정의 vi /etc/php.ini
파일에서 483번 라인을 On 해주면 된다.



(설정)



이렇게 되면 문자열 입력이 안된다.
한번 해보겠다.
단순히
download.php?id=gogo_test&page=1&page_num=20&category=&sn=off&ss=off&sc=off&keyword

=&prev_no=&select_arrange=headnum&desc=asc&no=19&filenum=1=100,%20me

mo=concat(memo,'injection test !')%20%23
이렇게 게시글에 injection test! 문자열을 추가해볼것이다.



(SQL Injection)



실행 후 SQL 로그를 확인해 보면




(로그 확인)




' 쿼터 앞에 \ (역슬래쉬)가 붙은 것을 볼 수 있다.
그래서 '가 문자열의 역할을 못하게 되어 SQL Injection이 되지 않았다.

=> 문자열 인젝션은 따옴표를 적어줘야하는데
여기서 magic_quotes_gpc 설정을 해주면 문자열 따옴표가 escape되서
문자열을 나타내지 못하게 된다.
그러므로 문자열 인젝션이 불가능하게 된다.
하지만 이걸 켜주게 되면
모든 입력에 대해 전부 체크하게 된다.
-> 쿼리문이 없더라도 입력값을 전부 체크하기 때문에 성능이 떨어지게 된다.
그렇기 때문에 사라진 것이다. 만들때 함수를 이용하여 체크할 수 있도록 해둔 것이다.
=> 설정에서 빠진 이유이다.



+ Recent posts