Notice
Recent Posts
Recent Comments
Link
IgnatiusHeo
구현단계 보안약점 제거 기준-경쟁조건: 검사 시점과 사용 시점(TOCTOU) 본문
작성일: 230706
※ 본 게시글은 학습 목적으로 행정안전부·KISA의 소프트웨어 보안약점 진단 가이드, 소프트웨어 개발보안 가이드를 참고하여 작성하였습니다.
정리 내용: 소프트웨어 보안약점 진단 가이드(406~414p)
구분 | - 시간 및 상태 |
설계단계 | |
개요 | 병렬시스템(멀티프로세스로 구현한 응용프로그램)에서는 자원(파일, 소켓 등)을 사용하기에 앞서 자원의 상태를 검사한다. 하지만, 자원을 사용하는 시점과 검사하는 시점이 다르기 때문에, 검사하는 시점(Time Of Check)에 존재하던 자원이 사용하던 시점(Time Of Use)에 사라지는 등 자원의 상태가 변하는 경우가 발생한다. 예를 들어, 프로세스 A와 B가 존재하는 병렬시스템 환경에서 프로세스 A는 자원사용(파일 읽기)에 앞서 해당 자원(파일)의 존재 여부를 검사(TOC) 한다. 이때는 프로세스 B가 해당 자원(파일)을 아직 사용(삭제)하지 않았기 때문에, 프로세스 A는 해당 자원(파일)이 존재한다고 판단한다. 그러나 프로세스 A가 자원 사용(파일읽기)을 시도하는 시점(TOU)에 해당 자원(파일)은 사용불가능 상태이기 때문에 오류 등이 발생할 수 있다. 이와 같이 하나의 자원에 대하여 동시에 검사시점과 사용시점이 달라 생기는 보안약점으로 인해 동기화 오류뿐만 아니라 교착상태 등과 같은 문제점이 발생할 수 있다. |
진단 세부사항 (설계단계) |
|
보안대책 (구현단계) |
공유자원(예: 파일)을 여러 프로세스가 접근하여 사용할 경우, 동기화 구문을 사용하여 한 번에 하나의 프로세스만 접근 가능하도록(synchronized, mutex 등) 하는 한편, 성능에 미치는 영향을 최소화하기 위해 임계코드 주변만 동기화 구문을 사용한다. |
진단방법 (구현단계) |
① 소스코드 상에 다음과 같이 공유자원(파일/폴더, 소켓, 드라이버 등)을 여러 프로세스가 사용하는지 확인한다. 이 때, 하나의 공유자원을 동시에 접근할 가능성이 존재한다면 취약하다고 판단하며, 동기화 구문 등을 사용할 경우 안전하다고 판단한다. 그 외 공유자원 억세스를 관리하는 pool 형태의 자체 모듈을 제작할 경우에도 안전하다고 판단한다. |
다. 코드예제
ㅇ 분석
1: class FileMgmtThread extends Thread {
2: private String manageType = "";
3: public FileMgmtThread (String type) {
4: manageType = type;
5: }
//멀티쓰레드 환경에서 공유자원에 여러프로세스가 사용하여 동시에 접근할 가능성이 있어 안전하지
않다.
6: public void run() {
7: try {
8: if (manageType.equals("READ")) {
9: File f = new File("Test_367.txt");
10: if (f.exists()) {
11: BufferedReader br = new BufferedReader(new FileReader(f));
12: br.close();
13: }
14: } else if (manageType.equals("DELETE")) {
15: File f = new File("Test_367.txt");
16: if (f.exists()) {
17: f.delete();
18: } else { … }
19: }
20: } catch (IOException e) { … }
21: }
22:}
23:public class CWE367 {
24: public static void main (String[] args) {
25: FileMgmtThread fileAccessThread = new FileMgmtThread("READ");
26: FileMgmtThread fileDeleteThread = new FileMgmtThread("DELETE");
//파일의 읽기와 삭제가 동시에 수행되어 안전하지 않다.
27: fileAccessThread.start();
28: fileDeleteThread.start();
29: }
30:}
ㅇ 내용
1. 파일 쓰레드 관리 -> 읽기 쓰기 동시에 수행됨
2. 카운트를 추가하던가 동기식으로 관리하던가 해야할듯
ㅇ 수정
1: class FileMgmtThread extends Thread {
2: private static final String SYNC = "SYNC";
3: private String manageType = "";
4: public FileMgmtThread (String type) {
5: manageType = type;
6: }
7: public void run() {
//멀티쓰레드 환경에서 synchronized를 사용하여 동시에 접근할 수 없도록 사용해야한다.
8: synchronized(SYNC) {
9: try {
10: if (manageType.equals("READ")) {
11: File f = new File("Test_367.txt");
12: if (f.exists()) {
13: BufferedReader br
14: = new BufferedReader(new FileReader(f));
15: br.close();
16: }
17: } else if (manageType.equals("DELETE")) {
18: File f = new File("Test_367.txt");
19: if (f.exists()) {
20: f.delete();
21: } else { … }
22: }
23: } catch (IOException e) { … }
24: }
25: }
26:}
27:public class CWE367 {
28: public static void main (String[] args) {
29: FileMgmtThread fileAccessThread = new FileMgmtThread("READ");
30: FileMgmtThread fileDeleteThread = new FileMgmtThread("DELETE");
31: fileAccessThread.start();
32: fileDeleteThread.start();
33: }
34:}
ㅇ 내용
1. 동기화 추가
ㅇ 분석
//멀티쓰레드 환경에서 동시에 접근할 수 없도록 사용해야한다.
1: public void ReadFile(String f)
2: {
3: if(File.Exists(f))
4: {
5: File.ReadAllLines(f);
6: }
7: }
ㅇ 내용
1. 파일 읽기도 안되나? 다른 유저가 수정 중일 가능성때문에 그런가?
2. 그러면 파일 읽기 시 사본 생성 후 읽기 or 상태변경 중 여부를 확인해서 처리해야할듯.
ㅇ 수정
//멀티쓰레드 환경에서 동시에 접근할 수 없도록 사용해야한다.
1: [MethodImpl(MethodImplOptions.Synchronized)]
2: public void ReadFile(String f)
3: {
4: if(File.Exists(f))
5: {
6: File.ReadAllLines(f);
7: }
8: }
ㅇ 내용
1. MethodImpl 속성이 메서드 동기화 지정을 나타낸다함.
ㅇ 분석
1: static volatile double account;
2: void deposit(int amount) {
// lock 없이 공유 자원에 접근
3: account += amount;
4: }
5: void withdraw(int amount) {
6: account -= amount;
7: }
ㅇ 내용
1. volatile은 변수를 캐싱하지 않고 직접 접근해서 사용함. 이렇게 하면 장점 = 변수가 수정되는 즉시 확인이 가능함
ㅇ 수정
1: static volatile double account;
2: static mtx_t account_lock;
3: void deposit(int amount) {
// mutex_lock, mutex_unlock을 이용해 공유 자원 접근을 제한한다.
4: mutex_lock(&account_lock);
5: account += amount;
6: mutex_unlock(&account_lock);
7: }
8: void withdraw(int amount) {
9: mutex_lock(&account_lock);
10: account -= amount;
11: mutex_unlock(&account_lock);
12:}
ㅇ 내용
1. Lock 키워드를 사용해서 공유자원에 대한 동시 접근을 제한함
끝.
'자격 > SW보안약점진단원' 카테고리의 다른 글
구현단계 보안약점 제거 기준-오류 메시지 정보노출 (0) | 2023.07.06 |
---|---|
구현단계 보안약점 제거 기준-종료되지 않는 반복문 또는 재귀 함수 (0) | 2023.07.06 |
구현단계 보안약점 제거 기준-반복된 인증시도 제한 기능 부재 (0) | 2023.07.06 |
구현단계 보안약점 제거 기준-무결성 검사 없는 코드 다운로드 (0) | 2023.07.06 |
구현단계 보안약점 제거 기준-솔트 없이 일방향 해쉬 함수 사용 (0) | 2023.07.06 |