
Apache Spark 4.2.0 - उच्च - रिमोट - विशेषाधिकार अवशेष - प्रक्रिया-वैश्विक Python डेटा स्रोत मैप
abraxaslabs.tech · github.com/abraxas · @abraxas_null · [email protected] · spark-python-ds-static
राइट-अप: https://abraxaslabs.tech/research/spark-python-ds-static
वर्ग: विशेषाधिकार अवशेष पहुँच: रिमोट
Apache Spark 4.2.0 (32f72996) - Apache Software Foundation
DataSourceManager.dataSourceBuilders एक JVM-वैश्विक फ़र्स्ट-विन्स मैप है। SPARK-45917 लुकअप वर्कर के sys.path से pyspark_* Python Data Sources को स्वतः-पंजीकृत करता है। Connect सत्र पृथक्करण आर्टिफ़ैक्ट्स को SparkFiles/<sessionUUID>/ के अंतर्गत रखता है, और प्रति-सत्र registerPython runtimeDataSourceBuilders पर ही रहता है। पहला लुकअप फिर भी ट्रिगर करने वाले सत्र की SparkFiles डायरेक्टरी को sys.path पर डालता है, प्रत्येक DefaultSource को पिकल करता है, और उन क्लासों को कम्पैनियन ऑब्जेक्ट में कैश करता है। बाद में Connect SQL (या Hive Thrift SQL) read.format(name) / USING name उस क्लास को Spark UID के रूप में चलाता है, बिना Python प्रोटो भेजे।
प्लांटर एक Connect Python टेनेंट है जिसे पहले से ही Python की अनुमति है। पीड़ित उसी Connect ड्राइवर पर एक केवल-SQL टेनेंट है। Java उपनाम (parquet, csv, json, orc, jdbc) Java ServiceLoader पथ पर ही रहते हैं। मैप भर जाने के बाद के प्लांट रीफ़्रेश नहीं होते। AC:H पहला-लुकअप और एक ऐसा नाम है जो Java उपनाम नहीं है।
| ID | अभी कोई CVE नहीं |
| वर्ग | विशेषाधिकार अवशेष (क्रॉस-सत्र Python Data Source, Spark UID के रूप में; अन-प्रमाणित जॉब सबमिट नहीं) |
| पहुँच | रिमोट (साझा Spark Connect ड्राइवर) |
| CWE | CWE-269, CWE-502 |
| CVSS | उच्च: 8.8 CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:C/C:H/I:H/A:H |
| उत्पाद | Apache Spark |
| प्रभावित | 4.2.0 (32f7299601108917fb01920a54e084595b7b3bf8) Python Data Source स्टैटिक रजिस्ट्री |
| प्रमाणीकरण | Connect Python टेनेंट (प्लांटर) तथा बाद में एक केवल-SQL Connect / Hive Thrift SQL उपयोगकर्ता (पीड़ित) |
| लाइसेंस | GNU Affero GPL v3.0 |
| लैब | केवल 127.0.0.1:18970। विटनेस फ़ाइल। कम्पैनियन मैप का गैजेट। |
एक साझा ड्राइवर पर Spark Connect Python सत्र रखें। pyfiles/pyspark_<name>.py प्लांट करें जिसका DefaultSource.name() एक अनुपस्थित कनेक्टर शॉर्ट नाम (delta, iceberg, hudi, ...) हो। उस सत्र पर पहला Python Data Source लुकअप ट्रिगर करें। उसी JVM में बाद का प्रत्येक सत्र जो read.format(name) या SQL USING name करता है, उस पिकल की गई क्लास को Spark UID के रूप में ड्राइवर प्लानर वर्कर पर और एक्ज़ीक्यूटर पर इंस्टैंशिएट करता है।
यही पूरा विशेषाधिकार समुच्चय है। प्लांटर पहले से ही Python चलाता है। अवशेष यह है कि एक केवल-SQL टेनेंट, जिसने कभी REGISTER_DATA_SOURCE / Python UDF प्रोटो नहीं भेजा, फिर भी उस क्लास को निष्पादित करता है।
| विधि | सिंक | विशेषाधिकार |
|---|---|---|
प्लांटर: AddArtifacts नाम pyfiles/pyspark_<name>.py फिर पहला format(name) / लुकअप | कम्पैनियन DataSourceManager.dataSourceBuilders (DataSourceManager.scala ऑब्जेक्ट) तथा lookup_data_sources.py का pyspark_* का iter_modules | ट्रिगर करने वाले सत्र के पिकल किए गए DefaultSource को JVM-व्यापी कैश करें। लैब: layer='static' trigger='attacker' first-wins=yes। |
पीड़ित: SQL USING <name> / spark.read.format(name) ऐसे सत्र पर जिसने कभी प्लांट नहीं किया | PythonDataSourceV2 createDataSourceInPython | उस क्लास को Spark UID के रूप में चलाएँ। लैब: planted_by='attacker' witness_written=True static-cross-session=yes। ओरेकल फ़ाइल में SPARK-PYTHON-DS-STATIC-WITNESS है। |
| विधि | सिंक | परिणाम |
|---|---|---|
| मैप भर जाने के बाद किसी दूसरे नाम का बाद में लगाया गया प्लांट | वही स्टैटिक मैप | बंद। पहला-जीतता-है। लैब: later-lookup found=False, साथी अभी भी केवल delta। |
प्रति-सत्र registerPython("alpha") | runtimeDataSourceBuilders | पृथक। क्लोन केवल रनटाइम की प्रतिलिपि बनाता है। लैब: runtime-isolated=yes। alpha का विक्टिम पाठ found=False है। |
Java उपनाम parquet | Java DataSourceRegister ServiceLoader | बंद। लैब: java-alias-closed=yes layer='java'। csv/json/orc/jdbc के लिए भी वही। |
| विधि | सिंक | विशेषाधिकार |
|---|---|---|
प्लांट के बाद विक्टिम USING | ड्राइवर + एक्ज़ीक्यूटर Python वर्कर | Spark UID के रूप में क्लस्टर-व्यापी कोड। लैब पेलोड के बजाय एक साक्षी फ़ाइल लिखता है। |
| वही पथ | वर्कर क्रैश / स्पिन | Spark UID के रूप में उपलब्धता। High नहीं। High कोड एक्ज़ीक्यूशन है। |
साझा SparkSession पर Hive Thrift SQL USING | वही स्टैटिक मैप | वही अवशेष यदि Thrift और Connect ड्राइवर JVM साझा करते हैं। अभ्यास नहीं किया गया। |
parquet / csv / json / orc / jdbc हाईजैक। ServiceLoader जीतता है।concatenatePaths .. और निरपेक्ष नामों को अस्वीकार करता है)।pythonExec। Connect प्लानर सर्वर PYSPARK_PYTHON / python3 का उपयोग करता है।registerPython का क्रॉस-सत्र लीक। रनटाइम मैप प्रति DataSourceManager इंस्टेंस है।pyspark एक सत्र के साथ। कोई अन्य टेनेंट नहीं है।मैंने apache/spark v4.2.0 (32f7299601108917fb01920a54e084595b7b3bf8) को पिन किया। अट्ठाईस स्रोत खोजें। उपयोगकर्ता कोड निष्पादित करने वाला जॉब सबमिट डिज़ाइन के अनुसार है। History Jackson, UI शेल, PySpark स्थानीय प्रतिरूपण, और स्टैंडअलोन RPC रिसीव-पथ इस पील पर बंद हैं। Connect आर्टिफ़ैक्ट pyfiles को सत्र UUID के अंतर्गत पृथक करते हैं। रनटाइम registerPython प्रति सत्र है। साथी ऑब्जेक्ट नहीं है।
SPARK-45917 PYTHONPATH से pyspark_* पैकेजों को स्वतः-पंजीकृत करता है। यह ऑपरेटर-स्थापित कनेक्टरों के लिए अभिप्रेत है। अवशेष यह है कि लुकअप वर्कर ट्रिगर करने वाले सत्र की SparkFiles डायरेक्टरी को भी sys.path.insert करता है (worker_util.setup_spark_files), फिर जो भी pyspark_* DefaultSource मिलता है उसे एक प्रोसेस-ग्लोबल मैप में पिकल करता है जो कभी रीफ़्रेश नहीं होता।
गलत मोड़: registerPython पृथकता को पूरी टेनेंट बाधा मानना। रनटाइम पृथक है। स्टैटिक नहीं।
cd lab
./run.sh
Loopback 127.0.0.1:18970. Compose प्रोजेक्ट spark-python-ds-static. Witness SPARK-PYTHON-DS-STATIC-WITNESS. object DataSourceManager का Python gadget और प्रति-सत्र runtime maps. pyspark_delta.py केवल attacker SparkFiles में plant करें. Attacker lookup companion को भरता है. बाद में iceberg का plant refresh नहीं करता. delta का victim read oracle लिखता है. registerPython("alpha") leak नहीं करता. Java parquet Java ही रहता है.
अंतिम पंक्ति:
SUCCESS SPARK-PYTHON-DS-STATIC static-cross-session=yes runtime-isolated=yes first-wins=yes java-alias-closed=yes SPARK-PYTHON-DS-STATIC-WITNESS