CIS 규정 준수 구성 및 확인

이 문서에서는 CIS 벤치마크가 무엇인지, 벤치마크가 Container-Optimized OS(COS)와 어떻게 관련이 있고, 인스턴스의 규정 준수 상태를 감사하는 방법과 장애 발생 시 문제를 해결하는 방법을 설명합니다.

개요

인터넷 보안 센터(CIS)는 다양한 플랫폼에 대한 보안 우수사례 권장사항을 위한 벤치마크를 출시합니다. Container-Optimized OS CIS 벤치마크는 Container-Optimized OS를 사용하여 강력한 보안 상태를 지원하는 인스턴스를 구성하기 위한 일련의 권장사항입니다. COS x86 및 Arm 이미지 모두 CIS를 준수합니다.

벤치마크 액세스

Container-Optimized OS CIS 벤치마크는 CIS 웹사이트에서 제공됩니다.

보안 권장사항 수준

CIS는 Container-Optimized OS에 대해 다음과 같은 권장사항 수준을 정의합니다.

레벨 1

이 수준의 권장사항은 대부분의 환경에 적용될 수 있습니다. 이 수준에는 다음과 같은 권장사항이 포함됩니다.

  • 주소 공간 레이아웃 무작위 순서 지정이 사용 설정됨
  • /tmp는 실행 가능한 바이너리를 실행하는 데 사용할 수 없음
  • 패킷 리디렉션 전송이 중지됨

레벨 2

이 수준의 권장사항은 수준 1 권장사항을 확장하므로 보다 엄격한 보안 환경을 제공합니다. 수준 2 권장사항은 애플리케이션 변경이 필요할 수 있으므로 모든 사례에 적용될 수 있는 것은 아닙니다. 적용하기 전에 환경의 수준 2에서 권장사항을 평가해야 합니다. 이 수준에는 다음과 같은 권장사항이 포함됩니다.

  • 모든 열린 포트에 방화벽 규칙이 있음
  • ICMP 리디렉션 및 라우터 공지는 허용되지 않음
  • 기본 사용자 셸 제한 시간은 900초 이하임

Container-Optimized OS에서 CIS 벤치마크를 준수하는 방법

Milestone 97부터 Container-Optimized OS 이미지는 기본적으로 CIS 수준 1을 준수하고 CIS 수준 2를 준수하는 옵션을 제공합니다. 또한 CIS 권장사항 수준에 따라 인스턴스를 감사하는 데 사용할 수 있는 스캐너를 제공합니다.

권장사항을 정의하는 CIS 구성은 /usr/share/google/security/cis-compliance/cis_config.textproto에 있습니다. CIS 스캐너는 구성을 사용하여 인스턴스의 규정 준수 상태를 확인합니다. CIS 수준 규정 준수 스캐너를 실행할 때마다 결과는 /var/lib/google/cis_scanner_scan_result.textproto에 기록됩니다. CIS 스캐너를 실행할 때마다 이 파일을 덮어씁니다. CIS 수준 1 또는 수준 2 스캔 중 하나라도 실패하면 cis_scanner_scan_result.textproto 파일에 실패한 모든 검사 목록이 포함됩니다.

인스턴스 규정 준수 상태 확인

Container-Optimized OS 이미지는 규정 준수 검사 및 구성을 위해 다음과 같은 systemd 서비스를 제공합니다.

  • cis-level1.service: 기본적으로 사용 설정되어 있으며 부팅 시 시작됩니다. 서비스가 시작되면 인스턴스가 CIS 수준 1을 준수하는지 확인합니다.
  • cis-level2.service: 기본적으로 사용 중지되어 있습니다. 이 서비스를 사용하면 CIS 수준 2를 준수하도록 인스턴스를 구성하고 수준 1 및 수준 2에 대한 준수 상태를 확인할 수 있습니다.

다음 섹션에서는 인스턴스의 규정 준수 상태를 확인하고 감사 프로세스를 자동화하는 방법을 설명합니다.

CIS 수준 1 규정 준수 상태 확인

인스턴스가 CIS 수준 1에 부합하는지 확인하려면 cis-level1.service 상태를 확인하세요.

systemctl status cis-level1

출력은 다음과 비슷합니다.

Reading scan config from /usr/share/google/security/cis-compliance/cis_config.textproto
Running scan of 62 benchmarks
Scan status: SUCCEEDED
Found 0 non-compliant benchmarks
Writing scan results to /var/lib/google/cis_scanner_scan_result.textproto

검사 결과 수준에 부합하지 않으면 CIS 규정 준수 수준 1/수준 2 확인 실패를 참조하세요.

cis-level1.service는 인스턴스가 부팅될 때 CIS 수준 1 규정 준수를 한 번만 확인합니다. 주기적인 규정 준수 확인을 구성하려면 CIS 규정 준수 상태를 주기적으로 확인을 참조하세요.

CIS 수준 2 규정 준수 및 확인 상태 구성

cis-level2 서비스를 사용하여 CIS 수준 2를 준수하도록 인스턴스를 구성하고 수준 1 및 수준 2 모두에 대해 준수 상태를 확인할 수 있습니다. systemd 서비스는 다음을 제외한 모든 CIS 수준 2 권장사항을 지원합니다.

  • 4.1.1.2 Logging이 실행 중인지 확인(ID: logging-service-running)

    이 권장사항은 기본적으로 선택 해제되어 있지만 /etc/cis-scanner/env_vars 파일에서 확인할 수 있는 선택 해제 목록에서 ID를 삭제하여 다시 사용 설정할 수 있습니다. 이 검사는 마일스톤 109 이상에만 존재합니다. 이전 마일스톤에서 Logging을 직접 사용 설정하면 이 권장사항을 준수할 수 있습니다. 선택 해제를 실행취소한 경우 cis-level2 서비스를 실행하면 fluent-bit 로깅을 시작하는 스크립트가 실행됩니다. 기본 로깅을 사용하지 않거나 자체 로깅을 사용하려면 logging-service-running을 선택 해제한 상태로 둡니다.

다음 권장사항의 경우 cis-level2 서비스는 인스턴스를 구성하지만 이러한 권장사항의 규정 준수 상태를 확인하지 않습니다.

  • 105 이하:

    • 3.3.1.1 IPv6 기본 거부 방화벽 정책 확인
    • 3.3.1.2 IPv6 루프백 트래픽이 구성되었는지 확인
    • 3.3.1.3 IPv6 아웃바운드 및 설정된 연결이 구성되었는지 확인
    • 3.3.1.4 모든 열린 포트에 IPv6 방화벽 규칙이 있는지 확인
    • 3.3.2.1 기본 거부 방화벽 정책 확인
    • 3.3.2.2 루프백 트래픽이 구성되었는지 확인
    • 3.3.2.3 아웃바운드 및 설정된 연결 구성하기
  • 109 이상:

    • 3.3.1.4 모든 열린 포트에 IPv6 방화벽 규칙이 있는지 확인

cis-level2 서비스는 기본적으로 사용 중지되어 있습니다. 서비스를 시작하려면 다음 명령어를 실행합니다.

systemctl start cis-level2.service

인스턴스가 성공적으로 구성되고 CIS 수준 2 권장사항을 준수하는지 확인하려면 cis-level2.service 상태를 확인하세요.

systemctl status cis-level2

출력은 다음과 비슷합니다.

Reading scan config from /usr/share/google/security/cis-compliance/cis_config.textproto
Running scan of 112 benchmarks
Scan status: SUCCEEDED
Found 0 non-compliant benchmarks
Writing scan results to /var/lib/google/cis_scanner_scan_result.textproto

인스턴스 구성이 실패하거나 규정을 준수하지 않는 검사가 발견되면 문제 해결을 참조하세요.

cis-level2 서비스는 인스턴스를 구성하고 CIS 수준 2 규정 준수를 한 번만 확인합니다. 주기적인 규정 준수 확인을 구성하려면 CIS 규정 준수 상태를 주기적으로 확인을 참조하세요.

주기적으로 CIS 규정 준수 상태 확인

Container-Optimized OS 이미지에는 CIS 규정 준수를 주기적으로 확인하도록 다음 서비스가 포함되어 있습니다.

  • cis-compliance-scanner.service: /etc/cis-scanner/env_vars에 정의된 환경 변수를 기반으로 규정 준수 상태를 확인합니다. 기본적으로 이 서비스는 CIS 수준 1 규정 준수를 확인하고 중지됩니다.
  • cis-compliance-scanner.timer: 주기적으로 cis-compliance-scanner.service를 실행합니다. 기본 기간은 하루에 한 번입니다.

스캐너 서비스 구성

cis-compliance-scanner.service/etc/cis-scanner/env_vars에 정의된 환경 변수를 기반으로 CIS 규정 준수 상태를 확인합니다. 기본적으로 이 서비스는 CIS 수준 1 규정 준수를 확인합니다.

CIS 수준 2 규정 준수를 확인하려면 /etc/cis-scanner/env_varsLEVEL 환경 변수를 2로 설정합니다. /etc/cis-scanner/env_vars 파일은 다음과 비슷합니다.

# cis-compliance-scanner.service environment variables
# The config file defines which checks to perform by cis_scanner
CONFIG="/usr/share/google/security/cis-compliance/cis_config.textproto"
# Where to store the result of the scan
RESULT="/var/lib/google/cis_scanner_scan_result.textproto"
# Upto which level to scan. It can be 1 or 2
LEVEL="2"
# Extra options that can be passed to cis_scanner
# For valid options, see output of `cis_scanner -h`
EXTRA_OPTIONS=""

타이머 구성

주기적인 규정 준수 스캔을 설정하려면 cis-compliance-scanner.timer 단위를 시작합니다.

systemctl start cis-compliance-scanner.timer

기본적으로 cis-compliance-scanner.timer는 하루에 한 번 cis-compliance-scanner.service를 시작합니다. 스캔 기간을 변경하려면 cis-compliance-scanner.timer 단위의 OnUnitActiveSec 필드를 재정의합니다.

sudo mkdir /etc/systemd/system/cis-compliance-scanner.timer.d
sudo tee /etc/systemd/system/cis-compliance-scanner.timer.d/override.conf <<EOF
[Unit]
Description=Run CIS Scanner once an hour
[Timer]
OnUnitActiveSec=1h
EOF

이 예시에서는 스캐너 기간을 1시간 간격으로 설정합니다.

변경사항을 적용하려면 systemd 단위를 새로고침합니다.

systemctl daemon-reload

특정 CIS 규정 준수 확인 선택 해제

CIS 수준 1 및 수준 2 권장사항은 대부분의 환경에 적용되도록 구성되어 있습니다. 그러나 일부 권장사항은 특정 환경에 적용되지 않을 수 있습니다. 특정 권장사항을 선택 해제하려면 /etc/cis-scanner/env_varsEXTRA_OPTIONS 환경 변수를 사용하세요.

다음 env_vars 파일 예시는 etc-passwd-permissions 권장사항을 선택 해제합니다.

# cis-compliance-scanner.service environment variables
# The config file defines which checks to perform by cis_scanner
CONFIG="/usr/share/google/security/cis-compliance/cis_config.textproto"
# Where to store the result of the scan
RESULT="/var/lib/google/cis_scanner_scan_result.textproto"
# Upto which level to scan. It can be 1 or 2
LEVEL="1"
# Extra options that can be passed to cis_scanner
# For valid options:`cis_scanner -h`
EXTRA_OPTIONS="--benchmark-opt-out-ids=etc-passwd-permissions"

CIS 규정 준수 상태 사용 설정 및 확인 자동화

cloud-init 또는 OS 정책을 사용하여 인스턴스에 대한 규정 준수 확인 프로세스를 자동화할 수 있습니다. 다음 예시에서는 각 도구의 몇 가지 사용 사례를 보여줍니다.

  • 예시 1: 하루에 한 번 CIS 수준 1 준수를 확인합니다.
  • 예시 2: 한 시간에 한 번 CIS 수준 1 준수를 확인합니다.
  • 예시 3: 하루에 한 번 CIS 수준 2 준수를 확인합니다.
  • 예시 4: 특정 CIS 규정 준수 확인 선택 해제합니다.

cloud-init 사용

다음 예시를 시도하기 전에 Cloud config 형식으로 cloud-init 사용의 안내에 따라 cloud-init로 COS 인스턴스를 구성하는 방법을 숙지하세요.

예시 1

다음 구성 예시에서는 기본 기간을 하루에 한 번으로 주기적 CIS 수준 1 스캔을 시작합니다.

#cloud-config

runcmd:
# Check the compliance status of the instance once a day.
- systemctl start cis-compliance-scanner.timer

예 2

다음 예시에서는 1시간에 한 번으로 주기적 CIS 수준 1 스캔을 구성합니다.

#cloud-config

# Override cis-compliance-scanner.timer with 1 hour frequency.
write_files:

- path: /etc/systemd/system/cis-compliance-scanner.timer.d/override.conf
  permissions: 0600
  owner: root
  content: |
    [Unit]
    Description=Run CIS Scanner once an hour

    [Timer]
    OnUnitActiveSec=1h

runcmd:
# Reload systemd units.
- systemctl daemon-reload
# Check the compliance status of the instance once an hour.
- systemctl start cis-compliance-scanner.timer

예 3

다음 예시에서는 기본 기간을 하루에 한 번으로 주기적 CIS 수준 2 스캔을 구성합니다.

#cloud-config

runcmd:
# Configure the instance for CIS level 2.
- systemctl start cis-level2.service
# Change the scan level to CIS Level 2.
- sed -i 's/^LEVEL=.*$/LEVEL="2"/' /etc/cis-scanner/env_vars
# Check the compliance status of the instance once a day.
- systemctl start cis-compliance-scanner.timer

예 4

다음 예시에서는 스캐너가 하루에 한 번 실행되도록 구성하고 특정 CIS 권장사항을 선택 해제합니다.

#cloud-config

runcmd:
# Opt-out of the etc-passwd-permissions check.
- sed -i 's/^EXTRA.*$/EXTRA_OPTIONS="--benchmark-opt-out-ids=etc-passwd-permissions"/' /etc/cis-scanner/env_vars
# Check the compliance of the instance once a day.
- systemctl start cis-compliance-scanner.timer

OS 정책 사용

OS 정책을 사용하여 CIS 벤치마크 스캔을 구성할 수 있습니다. 시작하기 전에 다음을 포함한 OS 정책에 익숙한지 확인합니다.

또한 배포할 수 있도록 다음 예시에 instanceFilterrollout 옵션을 추가해야 합니다.

예시 1

다음 구성 예시에서는 기본 기간을 하루에 한 번으로 주기적 CIS 수준 1 스캔을 시작합니다.

# An OS policy to check CIS level 1 compliance once a day.
id: ensure-cis-level1-compliance-once-a-day-policy
mode: ENFORCEMENT
resourceGroups:
  - resources:
      id: ensure-cis-level1-compliance-once-a-day
      exec:
        validate:
          interpreter: SHELL
          # If cis-compliance-scanner.service is active, return an exit code
          # 100 to indicate that the instance is in compliant state.
          # Otherwise, return an exit code of 101 to run `enforce` step.
          script: |-
            is_active=$(systemctl is-active cis-compliance-scanner.timer)
            result=$(systemctl show -p Result --value cis-compliance-scanner.service)

            if [ "$is_active" == "active" ] && [ "$result" == "success" ]; then
              exit 100;
            else
              exit 101;
            fi
        enforce:
          interpreter: SHELL
          # COS 97 images are by-default CIS Level 1 compliant and there is no
          # additional configuration needed. However, if certain changes
          # cause non-compliance because of the workload on the instance, this
          # section can be used to automate to make fixes. For example, the
          # workload might generate a file that does not comply with the
          # recommended file permissions.
          # Return an exit code of 100 to indicate that the desired changes
          # successfully applied.
          script: |-
            # optional <your code>
            # Check the compliance of the instance once a day.
            systemctl start cis-compliance-scanner.timer && exit 100

예 2

다음 예시에서는 1시간에 한 번으로 주기적 CIS 수준 1 스캔을 구성합니다.

# An OS policy to check CIS level 1 compliance once an hour.
id: ensure-cis-level1-compliance-once-an-hour-policy
mode: ENFORCEMENT
resourceGroups:
  - resources:
      id: ensure-cis-level1-compliance-once-an-hour
      exec:
        validate:
          interpreter: SHELL
          # If cis-compliance-scanner.service is active, return an exit code
          # 100 to indicate that the instance is in compliant state.
          # Otherwise, return an exit code of 101 to run `enforce` step.
          script: |-
            is_active=$(systemctl is-active cis-compliance-scanner.timer)
            result=$(systemctl show -p Result --value cis-compliance-scanner.service)

            if [ "$is_active" == "active" ] && [ "$result" == "success" ]; then
              exit 100;
            else
              exit 101;
            fi
        enforce:
          interpreter: SHELL
          # Return an exit code of 100 to indicate that the desired changes
          # were successfully applied.
          script: |-
            # Overwrite "OnUnitActiveSec" field of the
            # cis-compliance-scanner.timer to trigger
            # cis-compliance-scanner.service once an hour
            # instead of once a day.
            mkdir /etc/systemd/system/cis-compliance-scanner.timer.d
            tee /etc/systemd/system/cis-compliance-scanner.timer.d/override.conf <<EOF
            [Unit]
            Description=Run CIS Scanner once an hour

            [Timer]
            OnUnitActiveSec=1h
            EOF
            # Reload systemd units.
            systemctl daemon-reload
            # Check the compliance of the instance once an hour.
            systemctl start cis-compliance-scanner.timer && exit 100

예 3

다음 예시에서는 기본 기간을 하루에 한 번으로 주기적 CIS 수준 2 스캔을 구성합니다.

# An OS policy to check CIS level 2 compliance once a day.
id: ensure-cis-level2-compliance-once-a-day-policy
mode: ENFORCEMENT
resourceGroups:
  - resources:
      id: ensure-cis-level2-compliance-once-a-day
      exec:
        validate:
          interpreter: SHELL
          # If cis-compliance-scanner.service is active, return an exit code
          # 100 to indicate that the instance is in compliant state.
          # Otherwise, return an exit code of 101 to run `enforce` step.
          script: |-
            is_active=$(systemctl is-active cis-compliance-scanner.timer)
            result=$(systemctl show -p Result --value cis-compliance-scanner.service)

            if [ "$is_active" == "active" ] && [ "$result" == "success" ]; then
              exit 100;
            else
              exit 101;
            fi
        enforce:
          interpreter: SHELL
          # Return an exit code of 100 to indicate that the desired changes
          # were successfully applied.
          script: |-
            # Configure the instance for CIS level 2.
            systemctl start cis-level2.service
            # Change the scan level to 2.
            sed -i 's/^LEVEL=.*$/LEVEL="2"/' /etc/cis-scanner/env_vars
            # Check the compliance of the instance once a day.
            systemctl start cis-compliance-scanner.timer && exit 100

예 4

다음 예시에서는 스캐너가 하루에 한 번 실행되도록 구성하고 특정 CIS 권장사항을 선택 해제합니다.

# An OS policy to opt-out of CIS check and check compliance status once a day.
id: exclude-cis-check-and-check-compliance-once-a-day-policy
mode: ENFORCEMENT
resourceGroups:
  - resources:
      id: exclude-cis-check-and-check-compliance-once-a-day
      exec:
        validate:
          interpreter: SHELL
          # If cis-compliance-scanner.service is active, return an exit code
          # 100 to indicate that the instance is in compliant state.
          # Otherwise, return an exit code of 101 to run `enforce` step.
          script: |-
            is_active=$(systemctl is-active cis-compliance-scanner.timer)
            result=$(systemctl show -p Result --value cis-compliance-scanner.service)

            if [ "$is_active" == "active" ] && [ "$result" == "success" ]; then
              exit 100;
            else
              exit 101;
            fi
        enforce:
          interpreter: SHELL
          # Return an exit code of 100 to indicate that the desired changes
          # were successfully applied.
          script: |-
            # Opt-out of the etc-passwd-permissions check.
            sed -i 's/^EXTRA.*$/EXTRA_OPTIONS="--benchmark-opt-out-ids=etc-passwd-permissions"/' /etc/cis-scanner/env_vars &&
            # Check the compliance of the instance once a day.
            systemctl start cis-compliance-scanner.timer
            # Ensure cis-compliance-scanner completes before exiting
            PID=$(systemctl show --property MainPID --value cis-compliance-scanner.service) &&
            timeout 5m bash -c -- 'while [ -e /proc/'$PID' ]; do echo "CIS Scanner with PID:'$PID' is still running"; sleep 1; done' &&
            exit 100

문제 해결

이 섹션에서는 CIS 벤치마크 스캔과 관련된 문제를 해결하는 방법을 설명합니다.

CIS 수준 2 권장사항을 준수하도록 인스턴스를 구성할 수 없습니다.

cis-level2 서비스는 먼저 인스턴스에서 CIS 수준 2 권장사항을 준수하도록 구성한 후 CIS 수준 1 및 수준 2 모두를 준수하는지 확인합니다. 인스턴스 구성이 실패하면 cis-level2 서비스가 다음 오류 메시지와 함께 종료됩니다.

Job for cis-level2.service failed because the control process exited with error code.
See "systemctl status cis-level2.service" and "journalctl -xeu cis-level2.service" for details.

저널 로그에는 인스턴스에 적용하지 못해 cis-level2 시스템 서비스가 실패하게 된 경우에 대한 권장사항이 나와 있습니다.

CIS 규정 준수 수준 1 또는 수준 2 확인 실패

CIS 수준 규정 준수를 실행할 때마다 스캔 결과는 /var/lib/google/cis_scanner_scan_result.textproto에 기록됩니다. CIS 수준 1 또는 수준 2 스캔 중 하나라도 실패하면 textproto 파일에 다음 예시와 같이 실패한 모든 검사 목록이 포함됩니다.

cat /var/lib/google/cis_scanner_scan_result.textproto

# Output
start_time: {
  seconds: 1648241700
  nanos: 763152171
}
end_time: {
  seconds: 1648241700
  nanos: 812992527
}
scanner_version: "1.1.4.3"
benchmark_version: "1.0.0"
status: {
  status: SUCCEEDED
}
non_compliant_benchmarks: {
  id: "etc-passwd-permissions"
  compliance_occurrence: {
    non_compliant_files: {
      path: "/etc/passwd"
      reason: "File permission is 0664, expected the following bits to be set: 0444 and the following bits to be clear: 0133"
    }
  }
}
compliant_benchmarks:  {
  id:  "etc-passwd-permissions"
  compliance_occurrence:  {}
}

실패한 검사를 완화하려면 CIS 벤치마크를 사용하고 실패한 검사에 대한 Remediation 섹션의 단계를 따라 인스턴스를 준수하게 합니다. CIS 벤치마크에서 실패한 검사에 해당하는 권장사항을 찾으려면 /usr/share/google/security/cis-compliance/cis_config.textproto의 CIS 스캐너 구성 파일에서 non_compliant_benchmark's ID를 조회합니다.