
CodeQL for Python에서 CVE-2024-32022를 찾는 쿼리를 작성하며 첫 걸음을 내딛으세요.
두 가지 옵션 중 하나를 선택하여 워크숍 실습을 진행할 수 있습니다:
로컬 CodeQL 설치를 사용하여 워크숍 실습을 진행합니다.
git이 설치되어 있어야 합니다.curl -L -O "https://github.com/sylwia-budzynska/codeql-workshop/releases/download/v1/test-app-db.zip" curl -L -O "https://github.com/sylwia-budzynska/codeql-workshop/releases/download/v1/kohya_ss-db.zip"
3. VS Code에서: 파일 -> **작업 영역에서 열기...** `vscode-codeql-starter.code-workspace`
4. 계속: [CodeQL 데이터베이스 선택](#select-codeql-database)
5. 그런 다음 [설치 테스트](#test-your-installation)
### 옵션 B: GitHub Codespace
원격 GitHub Codespace를 사용하여 워크샵 연습을 진행합니다.
#### 사전 요구 사항
* GitHub 계정 ([무료 가입](https://github.com/))
* 브라우저 (전체 워크샵을 브라우저에서 수행 가능 - 가장 빠른 설정) 또는 로컬 머신에 설치된 [Visual Studio Code](https://code.visualstudio.com/download) (VS Code) 및 [GitHub Codespaces](https://marketplace.visualstudio.com/items?itemName=GitHub.codespaces) 확장 프로그램.
참고: Codespace 사용량은 첫 120시간(코어당)이 매월 무료이며, 이 워크샵에서는 4코어 코드스페이스를 사용합니다. (Pro 계정이 있다면 8코어 머신으로 전환하는 것을 권장합니다.)
#### 지침
1. [GitHub](https://github.com/login) 계정에 로그인
2. https://github.com/sylwia-budzynska/codeql-workshop 저장소로 이동
3. Code -> Codespaces 클릭
4. 더하기 기호(+)를 클릭하여 새 코드스페이스 생성
<img src="https://assets.kitploit.com/production/public/readmes/33098/c86e537f9e7891fb6bdb5da727cae5b6ad0b2c9ac94f67854d48296f2dad89cb.png" width="439" alt="스크린샷: Codespace 생성, 더하기 클릭">
VS Code가 브라우저에서 시작되고 원격 코드스페이스가 빌드됩니다. 몇 분 정도 걸릴 수 있습니다.
`vscode-codeql-starter.code-workspace` 작업 영역을 열 것인지 묻는 메시지가 나타나면 "작업 영역 열기"를 클릭합니다.
5. 로컬 VS Code를 사용하려면 왼쪽 위 모서리의 세 줄 버튼을 누르고 "Open VS Code Desktop"을 선택합니다. 이 옵션이 나타나는 데 최대 몇 분이 걸릴 수 있습니다.
<img src="https://assets.kitploit.com/production/public/readmes/33098/f2c8c2fe6da80142344b17c208da31a23c3fa68a3917a124f0e2f7871b6a20f7.png" width="300" alt="스크린샷: 세 줄 버튼을 누르고 'Open in VS Code Desktop' 선택">
6. 계속: [CodeQL 데이터베이스 선택](#select-codeql-database)
7. 그런 다음 [설치 테스트](#test-your-installation)
코드스페이스는 [github.com/codespaces](https://github.com/codespaces)에서 확인할 수 있습니다. 사용하지 않으면 몇 시간 후 자동으로 종료되지만, 120시간 무료 사용 시간을 초과하지 않도록 워크샵 후 [github.com/codespaces](https://github.com/codespaces) > 세 점 > "Stop codespace"를 기억하여 중지하세요.
#### 설치 문제 해결
다음과 같은 오류가 발생하는 경우:
* `Failed to run query: Could not resolve library path for [..]`
* `Could not resolve module [..]`
* `Could not resolve type [..]`
git 서브모듈(특히 ql 저장소)을 복제하는 것을 빼먹었을 가능성이 높습니다. 이 문제를 해결하려면 `git submodule init && git submodule update --recursive`를 실행합니다.
### CodeQL 데이터베이스 선택
1. VS Code에서 `vscode-codeql-starter.code-workspace` 작업 영역이 열려 있는지 확인합니다.
2. 왼쪽 탭 창에서 "QL" 아이콘을 클릭하여 CodeQL 보기로 이동합니다.
3. "Choose Database from Archive"를 클릭하고 저장소 루트에 있는 `test-app-db.zip` 파일을 선택합니다.
참고: 이 시점에 VS Code에서 CodeQL CLI를 설치하라는 팝업 메시지가 나타날 수 있습니다. 수락하면 문제가 해결됩니다. CLI 설치가 완료되면 위의 데이터베이스 선택을 완료할 수 있습니다.
<img src="https://assets.kitploit.com/production/public/readmes/33098/65cc5790b8b49113623bc9a9b34a1be61575b05bea2428c46f83115e2271148b.png" alt="스크린샷: CodeQL 관련 VS Code 오류 메시지">
<img src="https://assets.kitploit.com/production/public/readmes/33098/c3bf9c304d9c1f6199f591c9bcbf6e446ee4f5388ab209e30887326698129f84.png" alt="스크린샷: VS Code에서 CodeQL CLI 설치 중">
### 설치 테스트
#### 사전 요구 사항
이전에 선택한 CodeQL 데이터베이스가 CodeQL 보기에서 선택되어 있는지 확인합니다. (선택되지 않은 경우 "Select"를 클릭)
데이터베이스가 선택되면 다음과 같이 표시됩니다 (체크 표시 확인):
<img src="https://assets.kitploit.com/production/public/readmes/33098/fee6e47c0d9b0754c7ac9e29e2f0b3a721093aa5ce882615b3839a99f4862506.png" alt="스크린샷: CodeQL 데이터베이스 선택됨">
#### 지침
1. VS Code에서 `codeql-custom-queries-python` 작업 영역 폴더로 이동합니다.
2. 새 파일 `test.ql`을 생성합니다.
3. 다음 내용을 추가합니다: `select "Hello World!"`
4. 파일을 저장하고, 파일 영역에서 마우스 오른쪽 버튼을 클릭한 후 "CodeQL: Run Query on Selected Database"를 선택합니다.
5. 결과 "Hello World!"가 포함된 새 탭이 열려야 합니다.
## :books: 자료
- [QL 튜토리얼](https://codeql.github.com/docs/writing-codeql-queries/ql-tutorials/)
- [CodeQL for Python 언어 가이드](https://codeql.github.com/docs/codeql-language-guides/codeql-for-python/)
- [CodeQL 문서](https://codeql.github.com/docs/)
- [QL 언어 참조](https://codeql.github.com/docs/ql-language-reference/)
- [Python용 CodeQL 라이브러리](https://codeql.github.com/codeql-standard-libraries/python/)
- [Python 코드 기본 쿼리](https://codeql.github.com/docs/codeql-language-guides/basic-query-for-python-code/)
- [QL 클래스](https://codeql.github.com/docs/ql-language-reference/types/#classes)
- [CodeQL 제로부터 히어로까지 1부: 취약점 연구를 위한 정적 분석의 기초](https://github.blog/2023-03-31-codeql-zero-to-hero-part-1-the-fundamentals-of-static-analysis-for-vulnerability-research/)
- [CodeQL 제로부터 히어로까지 2부: CodeQL 시작하기](https://github.blog/2023-06-15-codeql-zero-to-hero-part-2-getting-started-with-codeql/)
- [CodeQL 제로부터 히어로까지 3부: 보안 연구](https://github.blog/2024-04-29-codeql-zero-to-hero-part-3-security-research-with-codeql/)
- [CodeQL 제로부터 히어로까지 4부: Gradio 사례 연구](https://github.blog/security/vulnerability-research/codeql-zero-to-hero-part-4-gradio-framework-case-study/)
- [CodeQL 제로부터 히어로까지 5부: 쿼리 디버깅](https://github.blog/security/vulnerability-research/codeql-zero-to-hero-part-5-debugging-queries/)
## 워크샵
"CodeQL로 취약점 찾기" 워크샵에 오신 것을 환영합니다!
이 세션에서는 보안 연구 및 정적 분석의 기초를 소개하며, 소프트웨어에서 취약점을 찾을 때 사용됩니다. 간단한 취약점 예제를 사용하여 CodeQL이 이를 어떻게 감지할 수 있는지 살펴보고, 참가자가 스스로 CodeQL을 사용하여 취약점을 찾는 방법에 대한 예제를 제공합니다.
시작하기 전에 모든 사전 요구 사항이 충족되어 워크샵에 참여할 수 있는지 확인하는 것이 중요합니다.
워크샵은 여러 섹션으로 나뉘며, 각 섹션은 최종 쿼리로 이어지는 연습 문제로 구성됩니다.
각 섹션에 대해 사용할 수 있는 QL 클래스 및 멤버 조건자에 대한 참조를 제공하는 *가이드라인*을 제공하여 연습 문제를 완료하는 데 도움을 줍니다.
### 개요
이 워크샵에서는 [kohya_ss](https://securitylab.github.com/advisories/GHSL-2024-019_GHSL-2024-024_kohya_ss/)의 알려진 *명령 삽입 취약점*을 찾을 것입니다. 이러한 취약점은 사용자가 제어하는 정보가 안전하지 않은 방식으로 명령을 구성하고 실행하는 애플리케이션 코드에 도달할 때 발생할 수 있습니다. 사용자 입력으로부터 안전하지 않게 구성된 명령은 의도하지 않은 동작(예: 임의 명령 실행, 민감한 정보 노출)을 수행하도록 변경될 수 있습니다.
이 워크샵에서 논의되는 명령 삽입은 [CVE-2024-32022, CVE-2024-32026, CVE-2024-32025, CVE-2024-32027](https://securitylab.github.com/advisories/GHSL-2024-019_GHSL-2024-024_kohya_ss/) 입니다.
## 이론
### 소스와 싱크
가장 잘 알려진 취약점 중 하나인 명령 삽입에 대해 생각해보십시오. 이는 사용자 입력이 서버에서 직접 셸 명령을 실행할 수 있는 함수에 사용될 때 발생합니다. 이를 통해 공격자는 애플리케이션을 실행하는 서버에서 운영 체제(OS) 명령을 실행할 수 있으며, 일반적으로 애플리케이션과 그 데이터를 완전히 손상시킬 수 있습니다.
삽입 취약점의 주요 원인은 신뢰할 수 없는 사용자 제어 입력이 프로그램의 민감하거나 위험한 함수에 사용되는 것입니다. 정적 분석에서 이를 나타내기 위해 데이터 흐름, 소스, 싱크와 같은 용어를 사용합니다.
사용자 입력은 일반적으로 애플리케이션의 진입점, 즉 데이터의 출처에서 비롯됩니다. 여기에는 GET 및 POST와 같은 HTTP 메서드의 매개변수 또는 프로그램의 명령줄 인수가 포함됩니다. 이를 "**소스**"라고 합니다.
명령 삽입의 예를 계속 들자면, 무해화되지 않은 신뢰할 수 없는 데이터와 함께 호출되어서는 안 되는 위험한 함수의 예로는 `os.system`이 있습니다. 이러한 위험한 함수를 "**싱크**"라고 합니다. 함수가 잠재적으로 위험하다고 해서 즉시 악용 가능한 취약점이거나 제거해야 한다는 의미는 아닙니다. 많은 싱크에는 안전하게 사용하는 방법이 있습니다. 사용자 입력과 함께 사용되어서는 안 되는 싱크의 다른 예로는 Python의 MySQLdb 라이브러리의 MySQLCursor.execute() (SQL 삽입 유발) 또는 Python의 eval() 내장 함수 (임의 표현식 평가, 코드 삽입 유발)가 있습니다.
취약점이 존재하려면 안전하지 않은 사용자 제어 입력이 적절한 무해화 또는 입력 검증 없이 위험한 함수에 사용되어야 합니다. 즉, 소스와 싱크 사이에 코드 경로가 있어야 하며, 이 경우 데이터가 소스에서 싱크로 흐른다고 말합니다. 즉, 소스에서 싱크로 "**데이터 흐름**"이 있습니다.
<img src="https://assets.kitploit.com/production/public/readmes/33098/ff60a1649737805a71bd27710209dba66203a77159cc72ae435c165353e56491.png">