CodeQL용 데이터베이스 준비

완료됨

CodeQL은 코드를 데이터와 같이 처리합니다. CodeQL 분석은 코드에서 관계형 데이터를 추출하고 이를 사용하여 CodeQL 데이터베이스를 빌드하는 데 의존합니다. 이러한 데이터베이스에는 코드베이스에 대한 모든 중요한 정보가 포함됩니다.

그런 다음, 이 데이터베이스에 대해 CodeQL 쿼리를 실행하여 보안 취약성, 버그 및 기타 오류를 식별할 수 있습니다. 사용자 고유의 쿼리를 작성하거나 GitHub 연구원 및 커뮤니티 기여자가 작성한 표준 CodeQL 쿼리를 실행할 수 있습니다.

독립 실행형 CodeQL CLI를 사용하여 CodeQL 데이터베이스를 만들고 분석할 수 있습니다. 데이터베이스를 분석하면 SARIF(정적 분석 결과 교환 형식)가 생성되며, 경고 세부 정보를 보기 위해 GitHub 리포지토리에 업로드할 수 있습니다.

CodeQL 검색 아키텍처

CodeQL 검색은 소스 코드를 쿼리 가능한 데이터로 변환하고, 보안 쿼리를 실행하고, 결과를 코드 검색 경고로 게시하는 파이프라인을 따릅니다.

검사 워크플로는 다음과 같습니다.

  1. 소스 코드: CodeQL은 분석 중인 커밋의 리포지토리 콘텐츠로 시작합니다.
  2. 추출: 언어별 추출기는 코드를 읽고 소스 파일, 구문, 제어 흐름 및 데이터 흐름에 대한 팩트를 수집합니다.
  3. 데이터베이스 만들기: 추출된 팩트는 CodeQL 데이터베이스에 저장됩니다. 각 데이터베이스는 코드베이스에서 하나의 언어를 나타냅니다.
  4. 쿼리 실행: CodeQL은 GitHub 유지 관리 쿼리, 커뮤니티 쿼리 또는 사용자 지정 쿼리를 데이터베이스에 대해 실행합니다.
  5. SARIF 생성: 쿼리 결과는 SARIF(정적 분석 결과 교환 형식)로 작성됩니다.
  6. GitHub 코드 검색: SARIF 결과가 GitHub 업로드되고 코드 검색 경고로 표시됩니다.

이 아키텍처는 코드 추출과 쿼리 실행을 구분합니다. 데이터베이스를 만든 후에는 코드를 다시 추출하지 않고도 동일한 데이터베이스에 대해 다른 쿼리 그룹을 실행할 수 있습니다.

언어 전략

CodeQL은 컴파일된 언어와 해석된 언어를 모두 지원하지만 추출 전략은 언어 유형에 따라 달라집니다.

컴파일된 언어

다음과 같은 컴파일된 언어의 경우:

  • C/C++
  • C#
  • Java
  • Kotlin
  • 러스트
  • 재빠르다
  • Go

CodeQL은 종종 프로젝트가 빌드되는 방식을 이해해야 합니다. 데이터베이스를 만드는 동안 CodeQL은 컴파일러에서 처리된 원본 파일을 추출할 수 있도록 빌드 프로세스를 모니터링할 수 있습니다.

가장 안정적인 결과를 얻으려면 autobuild 또는 no build 옵션에 의존하기보다는 명시적인 빌드 명령을 설정하세요.

해석된 언어

다음과 같은 해석된 언어의 경우:

  • Python
  • 자바스크립트/타입스크립트
  • Ruby

CodeQL은 별도의 빌드 명령 없이 소스 코드에서 직접 정보를 추출합니다.

다중 언어 리포지토리

지원되는 여러 언어가 포함된 리포지토리의 경우:

  • 각 언어에 대해 별도의 데이터베이스를 만듭니다.
  • GitHub Actions 각 언어가 올바르게 초기화, 추출 및 분석되도록 언어 행렬을 사용합니다.

CodeQL에 대한 데이터베이스 준비

CodeQL 데이터베이스를 생성하기 전에:

  1. CodeQL CLI를 설치하고 구성합니다.
  2. 분석하려는 코드베이스의 버전을 확인합니다.

컴파일된 언어의 경우:

  • 프로젝트를 빌드할 준비가 되었는지 확인합니다.
  • 필요한 모든 종속성을 미리 설치합니다.
  • CodeQL은 모든 원본 파일의 관계형 표현을 추출하여 데이터베이스를 만듭니다.

해석된 언어의 경우:

  • 추출기는 소스 코드에서 직접 실행됩니다.
  • 종속성은 추출 중에 자동으로 확인됩니다.

컴파일된 언어의 경우 CodeQL은 일반 빌드 프로세스를 모니터링합니다. 컴파일러가 소스 파일을 처리할 때마다 CodeQL은 복사본을 만들고 분석에 필요한 모든 관련 정보를 추출합니다.

CLI 설정

다음 단계에 따라 CodeQL CLI를 설치합니다.

1. CodeQL CLI 번들 다운로드

권장 설치 방법은 번들 패키지를 다운로드하여 CLI, 라이브러리 및 쿼리 팩 간의 호환성을 보장하는 것입니다.

번들에는 다음이 포함됩니다.

  • CodeQL CLI
  • 호환되는 CodeQL 쿼리 및 라이브러리
  • 미리 컴파일된 쿼리 팩

번들을 다운로드하려면:

  1. CodeQL 공용 리포지토리의 릴리스 페이지로 이동합니다.
  2. 자산에서 플랫폼별 번들을 다운로드합니다.

릴리스 페이지에는 다음도 포함됩니다.

  • 출시 정보
  • 이전 버전
  • codeql-bundle.tar.gz모든 플랫폼을 지원하는 입니다.

2. 보관 파일 추출

.zip 보관 파일을 원하는 디렉터리에 추출합니다.

macOS Catalina 이상 사용자는 CodeQL CLI 설명서에 설명된 대로 추가 설정 단계를 완료해야 합니다.

3. CodeQL 실행

추출 후 다음 중 하나를 수행합니다.

  • Run:
<extraction-root>/codeql/codeql

또는

  • 추가:
<extraction-root>/codeql

다음과 같이 간단히 CLI를 호출할 수 있도록 시스템에 PATH 적용합니다.

codeql

이제 CodeQL 명령을 실행할 수 있습니다.

CLI 설정 확인

다음 명령을 실행하여 설치가 제대로 작동하는지 확인합니다.

설치된 CodeQL 팩 표시:

codeql resolve packs

실행 파일이 PATH에 없으면 다음을 사용하세요.

<extraction-root>/codeql/codeql resolve packs

필요한 언어 팩이 누락된 경우 독립 실행형 CLI가 아닌 CodeQL 번들을 다운로드했는지 확인합니다.

지원되는 언어 표시:

codeql resolve languages

데이터베이스 만들기

프로젝트의 루트에서 CodeQL 데이터베이스를 만듭니다.

codeql database create <database> --language=<language-identifier>

교체하십시오

  • <database> 대상 디렉터리를 사용합니다.
  • 분석할 언어 식별자가 포함된 <language-identifier>

다음 옵션을 사용할 수도 있습니다.

옵션 Purpose
--source-root 소스 코드를 포함하는 루트 디렉터리를 지정합니다.
--db-cluster 여러 언어에 대한 데이터베이스를 만듭니다.
--command 컴파일된 언어에 대한 빌드 명령을 지정합니다. Python, Ruby 또는 JavaScript에는 필요하지 않습니다.
--no-run-unnecessary-builds 와 함께 --db-cluster사용할 때 불필요한 빌드를 건너뜁니다.

성공적으로 실행된 후:

  • 새 데이터베이스 디렉터리가 만들어집니다.
  • 사용하는 --db-cluster경우 각 언어에 대해 하위 디렉터리가 만들어집니다.

각 데이터베이스에는 다음이 포함됩니다.

  • 관계형 분석 데이터
  • 원본 보관
  • CodeQL 분석에 필요한 메타데이터

원본 보관 파일은 데이터베이스를 만들 때 원본 파일의 스냅샷이며 분석 결과를 표시할 때 사용됩니다.

데이터베이스 생성 및 성능 고려 사항

CodeQL 데이터베이스를 만든 후에는 데이터베이스 생성이 작동하는 방식과 데이터베이스 생성이 성능에 미치는 영향을 이해하는 것이 중요합니다.

데이터베이스 생성 방법

다음 중 하나를 사용하여 CodeQL 데이터베이스를 생성할 수 있습니다.

CodeQL 커맨드 라인 인터페이스 (CLI)

데이터베이스를 만들고 분석을 수동으로 실행합니다.

이 방법은 다음과 같은 경우에 유용합니다.

  • 지역 개발
  • Debugging
  • 고급 구성

GitHub Actions 워크플로들

대부분의 조직은 GitHub Actions 통해 데이터베이스 생성을 자동화합니다.

일반적인 워크플로:

  1. CodeQL을 초기화합니다.
  2. 데이터베이스를 만듭니다.
  3. 쿼리를 실행합니다.
  4. SARIF 결과를 GitHub 업로드합니다.

언어별 데이터베이스

CodeQL은 지원되는 모든 언어에 대해 별도의 데이터베이스를 만듭니다.

각 언어:

  • 자체 추출기를 사용합니다.
  • 자체 데이터베이스 스키마를 사용합니다.
  • 독립적으로 분석됩니다.

다중 언어 리포지토리의 경우 다음 중 하나를 수행합니다.

  • CLI에서 --db-cluster 옵션을 사용하세요.
  • GitHub Actions 언어 행렬을 구성합니다.

언어 매트릭스를 사용하면 병렬 분석 및 완전한 언어 검사를 수행할 수 있습니다.

컴파일된 언어에 대한 빌드 기반 추출

컴파일된 언어의 경우:

  • CodeQL은 빌드 프로세스를 모니터링합니다.
  • 빌드가 성공적으로 완료되어야 합니다.
  • 자동 자동 구축 은 모든 프로젝트에 대해 안정적으로 작동하지 않습니다.

최상의 결과를 위해 분석 전에 명시적 빌드 단계를 정의합니다.

해석된 언어의 경우 CodeQL은 빌드를 요구하지 않고 소스 코드에서 직접 추출합니다.

성능 고려 사항

데이터베이스 만들기 및 분석 시간은 몇 가지 요인에 따라 달라집니다.

리포지토리 크기

리포지토리가 클수록 추출 및 분석 시간이 더 많이 필요합니다.

여러 언어

언어 매트릭스를 사용하여 언어를 병렬로 분석하고 총 런타임을 줄입니다.

CI 리소스

CodeQL 분석은 리소스를 많이 사용할 수 있습니다.

러너의 CPU나 메모리를 늘리면 성능을 크게 향상시킬 수 있습니다.

분석 범위

예를 들어 다음을 제외하여 검사되는 코드를 제한하여 분석 시간을 줄일 수 있습니다.

  • 파일 테스트
  • 생성된 코드

일반적으로 분석 시간은 처리되는 소스 코드의 양에 비례합니다.

데이터베이스 만들기 및 다시 생성

CodeQL 데이터베이스는 특정 시점에 코드베이스의 스냅샷을 나타냅니다.

  • 각 분석 실행에 대해 새 데이터베이스가 만들어집니다.
  • 데이터베이스는 증분 방식으로 업데이트되지 않습니다.
  • 코드베이스를 변경하려면 새 데이터베이스가 필요합니다.

일반적으로 다음과 같은 경우 데이터베이스를 다시 생성합니다.

  • 새 커밋이 푸시됩니다.
  • 끌어오기 요청이 열리거나 업데이트됩니다.
  • 구성 변경 내용을 빌드합니다.
  • 쿼리 집합 또는 분석 구성의 변경 내용

데이터베이스 생성은 각 검사의 일부이므로 끌어오기 요청 또는 예약된 실행과 같은 의미 있는 이벤트에 검사를 맞추는 것이 중요합니다.

추출기

추출기는 CodeQL 데이터베이스를 빌드할 수 있는 각 입력 파일에 대한 관계형 데이터 및 소스 참조를 생성하는 도구입니다. CodeQL에서 지원하는 각 언어에는 하나의 추출기가 있습니다. 이 구조는 추출 프로세스가 가능한 한 정확하도록 합니다.

각 추출기는 고유한 구성 옵션 집합을 정의합니다. codeql resolve extractor --format=betterjson을(를) 입력하면 다음 예제와 같이 형식이 지정된 데이터가 생성됩니다.

{
  "extractor_root": "/home/user/codeql/java",
  "extractor_options": {
    "option1": {
      "title": "Java extractor option 1",
      "description": "An example string option for the Java extractor.",
      "type": "string",
      "pattern": "[a-z]+"
    },
    "group1": {
      "title": "Java extractor group 1",
      "description": "An example option group for the Java extractor.",
      "type": "object",
      "properties": {
        "option2": {
          "title": "Java extractor option 2",
          "description": "An example array option for the Java extractor",
          "type": "array",
          "pattern": "[1-9][0-9]*"
        }
      }
    }
  }
}

언어의 추출기에서 사용할 수 있는 옵션을 확인하려면 다음을 입력합니다.

  • codeql resolve languages --format=betterjson 또는
  • codeql resolve extractor --format=betterjson;

출력 형식은 betterjson 추출기 루트 및 기타 언어별 옵션도 제공합니다.

CodeQL 데이터베이스의 데이터

CodeQL 데이터베이스는 분석에 필요한 모든 데이터를 포함하는 단일 디렉터리입니다. 이 데이터에는 관계형 데이터, 복사된 원본 파일 및 데이터의 상호 관계를 지정하는 언어별 데이터베이스 스키마가 포함됩니다. CodeQL은 추출 후 이 데이터를 가져옵니다.

CodeQL 데이터베이스는 코드베이스에서 추출된 특정 언어의 쿼리 가능한 데이터의 스냅샷을 제공합니다. 이 데이터는 코드의 전체 계층적 표현입니다. 다음을 포함합니다.

  • AST(추상 구문 트리)의 표현입니다.
  • 데이터 흐름 그래프입니다.
  • 제어 흐름 그래프입니다.

데이터베이스는 여러 언어 코드베이스에 대해 한 번에 하나의 언어로 생성됩니다. 각 언어에는 고유한 데이터베이스 스키마가 있습니다. 스키마는 추출 프로세스 중에 초기 어휘 분석과 CodeQL을 통한 복잡한 분석 간의 인터페이스를 제공합니다.

CodeQL 데이터베이스에는 다음 두 개의 기본 테이블이 포함됩니다.

  • 테이블에는 빌드 프로세스 중에 CodeQL이 분석한 소스 코드의 모든 식에 대한 행이 포함되어 있습니다.
  • 테이블에는 빌드 프로세스 중에 CodeQL이 분석한 소스 코드의 모든 문에 대한 행이 포함되어 있습니다.

CodeQL 라이브러리는 이러한 각 테이블에 대한 추상화 계층을 제공하는 클래스를 정의합니다. 이 계층에는 관련 보조 테이블 ExprStmt.

잠재적인 CodeQL 결함

코드 검사 워크플로에서 데이터베이스를 만들면 몇 가지 잠재적인 부족이 있습니다. 이 섹션에서는 GitHub CodeQL 작업 사용에 대해 구체적으로 설명합니다.

행렬에 나열된 컴파일된 각 언어를 빌드하려면 자동 빌드에 언어 매트릭스를 사용해야 합니다. 행렬을 사용하여 둘 이상의 지원되는 프로그래밍 언어, 운영 체제 또는 도구 버전에 대한 작업을 만들 수 있습니다.

행렬을 사용하지 않는 경우 자동 빌드는 리포지토리에서 가장 많은 원본 파일을 사용하여 지원되는 컴파일된 언어를 빌드하려고 합니다. 분석 단계를 수행하기 전에 코드를 빌드하는 명시적 명령을 제공하지 않는 한 Go 이외의 컴파일된 언어 분석이 실패하는 경우가 많습니다.

자동 작성 단계의 동작은 언어 추출기가 실행되는 운영 체제에 따라 달라집니다. 자동 빌드 단계에서는 운영 체제에 따라 언어에 적합한 빌드 방법을 자동으로 검색하려고 합니다. 이 동작은 컴파일된 언어에 대한 신뢰할 수 없는 결과를 초래할 수 있으며 종종 실행이 실패할 수 있습니다.

자동 빌드에서 컴파일된 언어를 빌드하도록 하는 대신 분석 전에 실행되는 코드 검사 워크플로 파일 내에서 빌드 단계를 구성하는 것이 좋습니다. 이러한 방식으로 워크플로 파일은 보다 안정적인 검사를 위해 시스템 및 프로젝트의 빌드 요구 사항에 맞게 조정됩니다.

CodeQL 자동 작성 설명서에서 특정 언어 및 자동 작성 단계에 대해 자세히 읽을 수 있습니다.

VS 코드 확장

VS Code 1.39 이상을 사용하는 한 VS Code(Visual Studio Code) 및 CodeQL 확장을 사용하여 쿼리를 컴파일하고 실행할 수 있습니다. Visual Studio Code Marketplace에서 또는 CodeQL VSIX 파일을 다운로드하여 확장을 다운로드할 수 있습니다.

이 확장은 사용 가능한 경우 PATH에 설치된 CLI를 사용합니다. 그렇지 않은 경우 확장은 CLI의 실행 파일에 대한 액세스를 자동으로 관리합니다. 자동 관리를 사용하면 CLI가 CodeQL 확장과 호환됩니다.