시작 하며...
📌 참고 문헌
한국산학기술학회 /
A Method for Preventing CSRF Attacks in Web Application using Digital Signature Token
SK 쉴더스 / XSS란?
웹개발을 하다보면 자연스레 접하는 보안 관련 이슈들 중 CSRF와 XSS는 한번쯤은 자연스레 접해본 내용일 것이다.
이를 다시한번 자세히 복습해보는 차원에서 글을 작성하게 되었다.
실은 요즘에는 옛날과 달리 웹 애플리케이션을 빌드할 때 직접 구현해 사용하지 않는다. 신뢰도있는 수많은 기능들이 내장된 프레임워크, 라이브러리 등을 적극적으로 활용한다. (SpringBoot, Express, Django, React 등등..)
CSRF나 XSS는 정말 오래된 구닥다리(좋게 말하면 전통적인) 공격 기법이기에, 대부분의 최신 프레임워크에서는 개발자가 별도로 고려를 하지 않더라도 예방 처리가 되어 있다.
하지만 이것이 자동으로 예방되고 있었음을 알고 있다면 프레임워크 오픈소스 컨트리뷰터분들께 조금 더 감사한 마음을 가지고 사용할 수 있지 않을까?
그냥 구닥다리 기법이라고 할 수도 없는게, 2008년에 실제로 옥션에서 CSRF기법을 기반으로 한 공격으로 약 1800만명의 개인정보 유출사고가 발생했다.
CSRF (Cross Site Request Forgery)
사용자가 의도하지 않은 요청을 웹 애플리케이션에 전송하도록 만들어, 해커가 피해자의 권한을 도용하는 방법.
저 게시글 사이트의 도메인이 community.com 이라고 가정해보자.
이때 저 게시글의 링크를 클릭하고 아무런 반응이 일어나지 않았다. 사용자는 그냥 낚시인가 보다~ 하고 저 게시글을 떠났다.
하지만 사용자가 모르는 사이에 해당 사용자의 PW는 'fool'로 변경되었고, 해커는 이를 활용해 저 링크를 클릭한 사용자들의 비밀번호를 알아내게 되었다.
어떻게 한 것일까?
community.com의 비밀번호 변경 플로우가 다음과 같다고 가정해보자.
해커는 위 플로우를 먼저 Wireshark와 같은 패킷 분석 도구를 활용해 분석한다. 비밀번호 변경 요청을 보내면 어떤 요청이 발생하고, 어떤 응답이 서버에서 오는지 분석이 완료되면, 저 요청 플로우를 그대로 하나의 링크에 담아서 클릭을 유도하는 것이다.
이런식으로 a 태그 내에 숨겨서 사용 가능하다.
<a href="https://community.com/changePw?newPw=fool"> Click Me! </a>
심지어는 이런 방법도 가능하다.
이미지는 기본적으로 GET 요청을 보내 받아오기 때문에, 사용자는 이 이미지를 보는 것 만으로도
비밀번호 변경 요청이 발생한다.
<img src="https://community.com/changePw?newPw=fool">
이렇게 교묘한 방법들을 활용해서 다양한 동작들을 수행할 수 있다.
- 내 계정으로 돈을 송금하기
- 관리자 권한을 가진 사용자가 내 권한을 관리자로 승격시키기
이렇게 해커는 사용자의 정보를 탈취하거나 도용한 적 없이, 사용자가 해커가 원하는 동작을 몰래 수행하도록 하였기에, 서버에서는 비정상적인 요청임을 감지하기가 어렵다.
CSRF 예방 방법
HTTP 메서드 엄격 활용
옛날의 전통적인 WAS 애플리케이션에서는 HTTP 메서드에 대해서 엄격하게 분리하지 않고 단순히 요청 파라미터에 의존하는 경우가 있었는데, 이 경우에는 개발자가 POST 방식으로 구현한 기능도 GET 요청 + 쿼리파라미터로 동일한 동작이 발생할 수 있었다.
이처럼 반드시 WAS 애플리케이션에서는 요청의 메서드에 따라서 동작을 먼저 구분하고 처리해주면 단순한 CSRF 들은 예방할 수 있게 된다.
CSRF 토큰 사용
하지만 결국 사용자의 인증정보를 활용해 특정한 동작을 수행할 방법은 너무나 많기 때문에, 토큰을 활용한 방법을 제일 많이 사용한다.
서버가 각 요청마다 고유한 토큰을 사용자에게 발급하고, 이러한 토큰을 활용해 정상적인 사용자의 요청인지, 아니면 해커에 의해 비정상적으로 발생한 요청인지 구분하는 방법이다.
- 사용자가 community.com/changePw/form 페이지를 요청
- 서버는 응답으로 HTML 폼과 함께 CSRF 토큰을 포함시킴. (서버는 해당 사용자의 정보와 토큰을 함께 세션으로 저장)
- 사용자는 폼에 내용을 채워 CSRF 토큰과 함께 응답
- 정상 처리
해커는 사용자와 서버의 고유한 CSRF토큰을 알아낼 수 없기에, 일반적인 방법으로는 CSRF 공격에 실패한다.
SameSite 쿠키 활용
사용자의 인증정보를 보관하는 쿠키에 SameSite 속성을 부여하면, 해당 쿠키를 부여받은 사이트에서만 사용할 수 있다.
그렇기에 해커가 악의적으로 만든 가짜 피싱사이트에서 요청을 보내더라도 인증 쿠키가 포함되지 않기에 CSRF 공격을 방지할 수 있다.
XSS (Cross Site Scripting)
해커가 웹 페이지에 악성 스크립트를 삽입하여, 해당 페이지를 정상적으로 이용하려는 피해자들이 해당 악성 스크립트를 실행하도록 하는 방법.
만약 게시판에 누군가가 저런 게시글을 올려뒀다고 생각해보자.
황제를 의심한 죄는 상당히 무겁기에, 댓글로 응징해주기 위해서는 클릭할 수 밖에 없을 것이다.
이때 html 소스를 보면 다음과 같이 설정되어 있을 것이다.
<div class="post-title">
제목: 솔직히 페이커 윌른은 아니지 않나?
</div>
<div class="post-author">
작성자: 해커
</div>
<img class="post-image" src="이미지_경로.jpg" alt="전투 장면">
<div class="post-content">
미안하다 이거 보여주려고 어그로 끌었다...
<script>
sendUserTokenToServer();
</script>
</div>
이때 게시글 내용에 포함되어 있던 <script> 태그 내의 내용들이 자바스크립트로 인식되어 해당 게시글을 클릭하여 조회를 하러 온 사용자들의 환경에서 모두 sendUserTokenToServer()가 실행되어 버린다.
해커는 스크립트 실행이 가능한 것만 확인되면, 정말 무궁무진한 것들을 할 수 있다.
- 쿠키, 로컬 스토리지 등에 있는 사용자 인증 정보를 해커의 서버로 전송하게 만들기
- 가짜 폼을 생성하고, 해당 가짜 폼에 피해자의 민감한 정보를 입력하게 만들어 해커의 서버로 전송하게 만들기
이렇게 사용자는 자신도 모르게 페이지 내에서 외부인이 작성해둔 스크립트를 실행하는 셈이 되어버리고, 이는 곧 심각한 보안 문제로 이어진다.
XSS 예방 방법
이스케이핑
가장 먼저 게시글 내용에 태그와 같은 것들이 포함될 수 없도록 예방이 필요하다.
<, > 와 같은 특수문자들은 HTML Entity 에 의해 각각 <, > 와 같은 형태로 치환될 수 있다.
이를 활용해 서버에서는 게시글 내용으로 악용의 소지가 있는 특수문자가 오면 이스케이핑 처리하여 DB에 저장하고, 클라이언트는 해당 내용을 사용자에게 보여줄 때 정상적으로 다시 <, > 형태로 보여 준다.
즉, 사용자에게는 별 문제 없이 보이지만, 실제로는 치환된 문자로 DOM에 적용되어 스크립트로 인식되지 않게 한다.
Sanitizing
사용자에게 악의적인 의도가 없는 HTML 들은 사용하게 하고 싶을 수 있다.
예를 들자면 링크같은 것들이 될 수 있다.
깃허브 바로가기 < 이 요소를 개발자 도구로 찍어보면
<a data-mce-href="https://github.com/" href="https://github.com/" target="_blank">
깃허브 바로가기
</a>
이렇게 되어있는데, 이때 속성값을 활용해 이런 짓도 가능하다.
<a data-mce-href="https://github.com/" href="javascript:alert('XSS')" target="_blank">
깃허브 바로가기
</a>
이 처럼 HTML 내에서 JS 코드를 실행시키기 위한 방법은 수도없이 많기 때문에 이러한 내용들을 사전에 막아둔 라이브러
리나 화이트리스트들을 활용해 불순한 의도가 보이는 패턴을 발견할 시 없애 버릴 수 있다.
이러한 예방방법들을 조합해 링크, 이미지, 볼드체 등과 같이 일반적인 태그들은 사용자가 적절히 활용 가능함과 동시에 불순한 의도가 보이는 태그(수상한 script 실행 목적)들은 사전에 방지 해주어야 한다!
CSRF vs XSS
어려운 버전
CSRF : 공격자가 적법한 피해자의 권한을 가지고 정상적인 Request를 서버로 전달해 서버가 해당 동작을 승인
XSS : 공격자가 작성한 악성 스크립트가 피해자의 클라이언트 브라우저 환경에서 실행
박통 버전
CSRF : 일진이 학생에게 "네 돈으로 내빵을 사와라" 라고 시킴. (매점 아저씨는 이 학생이 괴롭힘을 당하는 아이인지 알 방법이 없음)
XSS : 일진이 학생의 돈을 빼앗고 직접 매점으로 가서 빵을 삼. (매점 아저씨가 살짝 의심할 수 있음.)
하지만 해킹이라는 것은 목적을 달성하기 위해 수많은 해킹 기법들을 함께 섞어 활용하기에, 위의 예시가 적절치 않을 수 있다. 그렇기에 여러가지 해킹 기법들을 사전에 숙지하고 있으면, 새로운 기법이 발생해도 금방 이해하고 보안 기술의 동향을 따라가기에 수월할 것이다.
'Computer Science > Security' 카테고리의 다른 글
SKT 해킹, BPF도어가 뭔데? (0) | 2025.05.03 |
---|---|
인증(Authentication)과 인가(Authorization)의 개념에 대해 (3) | 2024.01.04 |