
Apache Spark 4.2.0 - Élevé - À distance - Résidu de privilège - standalone REST ignore spark.authenticate
abraxaslabs.tech · github.com/abraxas · @abraxas_null · [email protected] · spark-rest-auth-bypass
Classe : Reliquat de privilège Portée : Distante
Apache Spark 4.2.0 (32f72996) - Apache Software Foundation
Le REST du Master autonome est activé par défaut sur le port 6066 et ne lit jamais spark.authenticate. CVE-2018-11770 promettait que le REST serait désactivé par défaut et un échec fermé si le secret RPC était défini alors que le REST était activé. Cette version a inversé les deux. MASTER_REST_SERVER_ENABLED vaut createWithDefault(true). Les filtres ne sont que MASTER_REST_SERVER_FILTERS, par défaut Nil. Un POST /v1/submissions/create non authentifié exécute le main de l'attaquant avec l'UID du Worker. Le Worker injecte _SPARK_AUTH_SECRET, donc la limitation de 2018 « driver sans exécuteurs » ne tient pas.
Il s'agit d'un reliquat de 11770, pas d'une nouvelle RCE CVE-2020-9480. Le RPC 7077 installe toujours AuthServerBootstrap. La soumission de job sur un cluster avec spark.authenticate=false est le comportement par défaut documenté et n'est pas ce bug.
| ID | pas encore de CVE |
| Classe | Reliquat de privilège (reliquat de CVE-2018-11770) |
| Portée | Distante (HTTP non authentifié vers le Master autonome 6066) |
| CWE | CWE-306, CWE-287 |
| CVSS | Élevé : 8.8 CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H |
| Produit | Apache Spark |
| Affecté | 4.2.0 (32f7299601108917fb01920a54e084595b7b3bf8) REST du Master autonome |
| Auth | aucune sur le REST. L'opérateur a défini spark.authenticate=true. REST laissé par défaut. |
| Licence | GNU Affero GPL v3.0 |
| Lab | 127.0.0.1:18900 uniquement. Image officielle spark:4.2.0. |
J'ai épinglé le tag v4.2.0, peel 32f7299601108917fb01920a54e084595b7b3bf8 (2026-07-11, v4.2.0-rc6). Pas master. Pas une RC 4.3.
Atteindre le REST du Master autonome sur 6066. Aucun en-tête Authorization. spark.authenticate est activé. spark.master.rest.filters n'est pas défini. Au moins un Worker est actif.
| Méthode | Point d'aboutissement | Privilège |
|---|---|---|
POST /v1/submissions/create non auth | RequestSubmitDriver (Master.scala:402-420) puis Worker DriverWrapper classForName(mainClass).main | Intégrité (prouvée en lab) : exécuter le mainClass de l'attaquant avec l'UID du Worker. Lab : driver RUNNING, fichier témoin. |
Même create ; Worker CommandUtils.buildLocalCommand | env du driver _SPARK_AUTH_SECRET | Intégrité (prouvée en lab) : le driver peut rejoindre par SASL le cluster RPC authentifié. Lab : injected=yes. |
GET /v1/submissions/status/{id} non auth | RequestDriverStatus (Master.scala:489-503) | Recon (prouvée en lab pour l'id créé) : état du driver / hôte du worker. |
GET /v1/submissions/readyz non auth | RequestReadyz | Recon (prouvée en lab) : Master non STANDBY. |
POST /v1/submissions/kill/{id} non auth | RequestKillDriver (Master.scala:422-453) | Intégrité + disponibilité (déduite) : arrêter le driver autonome d'un autre locataire. Même câblage de servlet non auth ; non exercé. |
POST /v1/submissions/killall non auth | RequestKillAllDrivers (Master.scala:455-478) | Disponibilité (déduite) : terminer tous les drivers autonomes en attente/en cours. Non exercé. |
POST /v1/submissions/clear non auth | RequestClearCompletedDriversAndApps | Intégrité (déduite) : supprimer la comptabilité des drivers/apps terminés. Non exercé. |
Prouvé en lab vs déduit : create, injection de secret, statut de son propre id et readyz sont prouvés en lab. Kill / killall / clear sont déduits de la même table de servlets non auth.
Nécessite : un Master autonome (pas YARN/K8s). L'opérateur a défini spark.authenticate=true. REST laissé par défaut (spark.master.rest.enabled true, spark.master.rest.filters non défini). Chemin réseau vers le Master 6066. Au moins un Worker. Pas le cluster documenté comme ouvert (spark.authenticate=false).
| Surface | Raison |
|---|---|
RPC 7077 avec spark.authenticate=true | AuthServerBootstrap toujours requis. Le chemin de réception de CVE-2020-9480 reste fermé. Pas une nouvelle RCE 9480. |
| JWSFilter lorsqu'il est défini | spark.master.rest.filters=org.apache.spark.ui.JWSFilter plus secretKey. Les tests renvoient 403 sans JWT. Opt-in. Par défaut Nil. |
UI doAs | nécessite toujours un admin. Le REST n'hérite pas des filtres de l'UI. |
| Shell UI CVE-2022-33891 | reliquat d'argv id -Gn fermé sur cette version. |
| Soumission YARN / Kubernetes | ce serveur REST est uniquement le Master autonome. |
Soumission de job avec spark.authenticate=false par défaut | FAQ : par conception. Pas ce reliquat. |
| REST Mesos | supprimé dans Spark 4.0. |
spark-submit CLI par défaut | utilise toujours le RPC 7077 (useRest vaut false par défaut de chaîne). --kill / --status sur spark:// utilisent toujours le REST. Le reliquat est l'écouteur du serveur. |
Le correctif de code de CVE-2018-11770 (SPARK-25088) était : REST désactivé par défaut, et require que le Master échoue fermé si spark.authenticate.secret est défini alors que le REST est activé. Cette version :