
phpMyAdmin 5.2.3 - 높음 - 원격 - CSRF - /sql에서 토큰 제거
abraxaslabs.tech · github.com/abraxas · @abraxas_null · [email protected] · phpmyadmin-csrf-sql
분석 문서: https://abraxaslabs.tech/research/phpmyadmin-csrf-sql
분류: CSRF 도달 범위: 원격
phpMyAdmin 5.2.3 (태그 RELEASE_5_2_3, 커밋 962857e). Common.php는 checkTokenRequestParam 이전에 전역 변수로부터 PSR-7 요청을 생성한다. 불일치 시 Sanitize::removeRequestVars는 $_POST와 $_GET을 지우지만 해당 스냅샷은 지우지 않는다. 그런 다음 $sql_query가 $request->getParsedBodyParam('sql_query')에서 복사된다. AJAX POST는 토큰 불일치 시 중단된다. 비 AJAX POST는 계속된다. SqlController는 제거된 $_POST['sql_query']를 우선시하고, 그렇지 않으면 전역 변수를 유지한다.
phpMyAdmin 세션 쿠키를 가진 피해자만 있으면 충분하다. sql_query를 포함하고 유효한 토큰이 없으며 ajax_request가 없는 상태로 index.php?route=/sql에 POST하면 된다. 해당 SELECT는 그 MySQL 사용자로 실행된다. 5.2.3의 기본 CookieSameSite=Strict는 많은 교차 사이트 브라우저를 차단한다. 동일 사이트, Lax, None 또는 HTTP 인증 환경에서는 여전히 공격이 성립한다. 어느 쪽이든 이는 깨진 CSRF 제어이다.
| ID | 아직 CVE 없음 |
| 분류 | CSRF |
| 도달 범위 | 원격. 기본 CookieSameSite=Strict는 많은 교차 사이트 브라우저를 차단한다. 동일 사이트 / Lax / None / HTTP 인증 환경에서는 여전히 성립한다. |
| CWE | CWE-352 |
| CVSS | 높음: 8.1 CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:N |
| 제품 | phpMyAdmin |
| 영향 받는 버전 | 5.2.3 태그 RELEASE_5_2_3 (962857e) |
| 인증 | 피해자 phpMyAdmin 세션 쿠키 (또는 HTTP 인증). 유효한 CSRF 토큰 없음. |
| 라이선스 | GNU Affero GPL v3.0 |
| 랩 | 127.0.0.1:19240 전용 |
피해자 브라우저가 ajax_request 없이 phpMyAdmin에 POST하도록 유도할 수 있는 사람은 누구든지 해당 MySQL 사용자로 SQL을 실행할 수 있다.
| 권한 | 메서드 / 경로 | 랩 검증 또는 추론 |
|---|---|---|
| 피해자 MySQL 계정으로 공격자 SQL 실행 (해당 SQL 박스의 무결성 + 정찰) | POST index.php?route=/sql sql_query=... db=... token 없음, ajax_request 없음 | 랩 검증. 결과 본문에 PMA-CSRF-SQL-WITNESS 포함. 일반 로그에 appuser로 SELECT 실행 기록됨 |
| AJAX에서 동일 핸들러 중단 | ajax_request=1을 포함한 동일 POST | 랩 검증. Token mismatch. INSERT 마커 행 없음. 일반 로그에 해당 INSERT 실행되지 않음 |
제거된 $_POST만 읽는 핸들러 우회 | 토큰 없이 POST /database/structure/drop-table | 랩 검증. keepme 여전히 존재 |
내보내기(SaveDir), 파티션 DROP/TRUNCATE, 계정 잠금, /config/set, pmadb 생성에서 동일한 격차 | 제거 후 PSR-7 본문을 읽는 모든 핸들러 | 추론. 검증하지 않음 |
이 랩에서 확인된 제외 항목: 인증되지 않은 PMA (먼저 쿠키 로그인 필요), AJAX 경로 (불일치 시 종료됨), 토큰 없는 drop-table, OS 셸. 기본 Strict SameSite는 전형적인 교차 사이트 폼이 종종 쿠키를 전송하지 않음을 의미한다. 남은 문제는 동일 사이트 및 Lax/None 배포 환경에서 여전히 실패한 CSRF 검사라는 점이다.
RELEASE_5_2_3에 대한 8개의 병렬 소스 탐색. Common.php는 checkTokenRequestParam() 이전에 $request = createFromGlobals()를 생성한다. 불일치 시 Sanitize::removeRequestVars()는 $_POST/$_GET만 지운다. 비 AJAX는 계속된다. SqlController는 $_POST가 비어 있으면 전역 $sql_query를 사용한다. 경로 GET|POST /sql.
잘못된 접근: AJAX /sql을 잔여물로 취급하는 것(이는 Token mismatch로 중단됨), drop-table을 잔여물로 취급하는 것(해당 핸들러는 제거된 $_POST만 읽음), 기본 Strict SameSite를 "CSRF는 종료됨"으로 취급하는 것(제어는 여전히 깨져 있으며 same-site / Lax / None이 남아 있음).
python3 phpmyadmin-csrf-sql-Abraxas-Labs.py
또는
cd lab
./run.sh
루프백 전용: http://127.0.0.1:19240. 이미지 phpmyadmin:5.2.3 및 mysql:8.0. Compose 프로젝트 phpmyadmin-csrf-sql. PoC는 동일 사이트 루프백 POST이다(Strict SameSite에서도 쿠키가 전송됨). 증거 PMA-CSRF-SQL-WITNESS.
SUCCESS phpmyadmin-csrf-sql sql-ran=yes ajax-abort=yes drop-held=yes PMA-CSRF-SQL-WITNESS
불일치가 발생하면 요청을 빈 본문으로 교체하거나, AJAX뿐만 아니라 모든 POST를 거부하십시오. 오래된 요청에서 sql_query를 복사하지 마십시오. 로그아웃처럼 fail closed 방식으로 처리하십시오.
962857e)libraries/classes/Common.phpSanitize::removeRequestVars는 $_POST/$_GET만 지움SqlController의 전역 $sql_queryGNU Affero GPL v3.0. LICENSE를 참조하십시오. 루프백 실험실 전용. 보증 없음.