[C#] SQL Injection 예방 코드
SQL Injection 이란 Web hacking 기법 중 하나입니다.
웹 애플리케이션의 뒷단에 있는 Database에 쿼리를 보내는 과정 사이에 일반적인 값 외에 악의적인 의도를 갖는 구문을 삽입하여 공격자가 원하는 SQL 쿼리문을 실행하는 기법입니다.
주로 사용자가 입력한 데이터를 제대로 필터링, 이스케이핑 하지 못했을 경우에 발생하며, 요즘의 거의 모든 데이터베이스 엔진은 유저 입력이 의도치 않은 동작을 하는 것을 방지하기 위해 Escape 함수와 Prepared Statement를 제공한다.
SQL Injection 공격의 종류
- 인증 우회 (AB : Auth ByPass)
- 데이터 노출 (DD : Data Disclosure)
- 원격 명령 실행 (RCE : Remote Command Excute)
인증 우회
아이디와 패스워드를 입력하는 로그인 페이지를 타겟으로 행해지는 공격
SQL 쿼리문의 true / false 의 논리적 연산 오류를 이용하여, 로그인 인증 쿼리문이 무조건 true 결과값이 나오게 하여 인증을 무력화 시키는 원리
[ 외부 입력값 ]
ID : admin'--
Password : 1234
[ 실행되는 쿼리문 ]
Select * From Users Where ID = 'admin'-- And Password = '1234'
데이터 노출
타겟 시스템의 주요 데이터 절취를 목적으로 하는 방식이다. Error based, Union based, Blind based, Time based 방식이 있다. 시스템의 에러는 개발자에게 버그를 수정하는 면에서 많은 도움을 주지만 역으로 에러를 이용할 수 있다. 악의적인 구문을 삽입하여 에러를 유발시키는 것이다.
해커는 GET 방식으로 동작하는 url에 추가적인 `query string`을 추가하여 에러를 발생시킬 수 있다. 이에 해당하는 오류가 나타난다면 그것을 가지고 데이터베이스의 구조를 유추할 수 있다. 그렇기 때문에 오류 페이지 또는 오류 메시지가 노출되어서는 안된다.
매개 변수화 된 쿼리를 사용하는 것은 3 단계 프로세스입니다.
- 매개 변수를 사용하여 SqlCommand 명령 문자열을 구성하십시오.
- 적절한 값을 할당하여 SqlParameter 개체를 선언하십시오.
- SqlParameter 개체를 SqlCommand 개체의 Parameters 속성에 할당하십시오.
SqlCommand와 SqlParameter를 사용하면 SQL_Injection에서 안전하게 코드를 작성할 수 있다.
SqlParameter 객체를 통해 전달되는 값은 쿼리에 영향을 끼치지 못하는 문자열로만 인식이 된다.
a or 1=1 -- 이런 코드도 "a or 1=1 --" 식의 문자열로 인식된다.
이런 방식을 Parameterized Query라고 함!
SqlConnection sCon = new SqlConnection("Data Source=000.000.000.000,1433;Initial Catalog=TestDB;User ID=admin;Password=password;Min Pool Size=5;Max Pool Size=100;Connect Timeout=5;Packet Size=8192");
sCon.Open();
SqlCommand sqlCom = new SqlCommand();
sqlCom.Connection = sCon;
sqlCom.CommandText = "select * from AccountTable where user_name=@userName and user_id=@userID";
sqlCom.CommandType = CommandType.Text;
sqlCom.Parameters.Add(new SqlParameter("@userName", SqlDbType.VarChar, 50)).Value = userName.Text;
sqlCom.Parameters.Add(new SqlParameter("@userID", SqlDbType.VarChar, 50)).Value = userID.Text;
SqlDataReader reader = sqlCom.ExecuteReader();
sCon.Close();
안전한 방식으로 쿼리를 필터링하려면 매개 변수를 사용해야합니다.
매개 변수를 사용하는 프로세스에는 세 가지 단계가 있습니다.
SqlCommand 명령 문자열에 매개 변수를 정의하고 해당 속성을 사용하여 SqlParameter 개체를 선언하고
SqlParameter 개체를 SqlCommand 개체에 할당합니다.
SqlCommand가 실행될 때 매개 변수는 SqlParameter 개체에 지정된 값으로 바뀝니다.
'Program Language > C#' 카테고리의 다른 글
[C#] MSBuild 빌드 시 C# 언어 버전 변경 (0) | 2020.03.26 |
---|---|
[C#] C#에서 unsafe 키워드 사용 방법 (0) | 2020.03.10 |
[C#] const와 readonly의 차이 (0) | 2020.02.06 |
[C#] EditorConfig를 이용한 코딩규칙 정형화 (0) | 2020.01.30 |
[C#] SonarQube - 정적분석 (0) | 2020.01.29 |