From 85b82e417d5ace6d58a0a4b8a36b4b177ed6cea8 Mon Sep 17 00:00:00 2001 From: Translator Date: Mon, 28 Jul 2025 18:12:53 +0000 Subject: [PATCH] Translated ['src/pentesting-web/deserialization/basic-java-deserializati --- ...ialization-objectinputstream-readobject.md | 81 +++++++++++++++++-- 1 file changed, 74 insertions(+), 7 deletions(-) diff --git a/src/pentesting-web/deserialization/basic-java-deserialization-objectinputstream-readobject.md b/src/pentesting-web/deserialization/basic-java-deserialization-objectinputstream-readobject.md index 0a0b9a0b7..7a2900118 100644 --- a/src/pentesting-web/deserialization/basic-java-deserialization-objectinputstream-readobject.md +++ b/src/pentesting-web/deserialization/basic-java-deserialization-objectinputstream-readobject.md @@ -1,15 +1,27 @@ +# Basic Java Deserialization with ObjectInputStream readObject + {{#include ../../banners/hacktricks-training.md}} -Σε αυτήν την ανάρτηση θα εξηγηθεί ένα παράδειγμα χρησιμοποιώντας `java.io.Serializable`. +Σε αυτή την ανάρτηση θα εξηγηθεί ένα παράδειγμα χρησιμοποιώντας `java.io.Serializable` **και γιατί η υπερχείλιση του `readObject()` μπορεί να είναι εξαιρετικά επικίνδυνη αν το εισερχόμενο ρεύμα ελέγχεται από επιτιθέμενο**. -# Serializable +## Serializable -Η διεπαφή Java `Serializable` (`java.io.Serializable` είναι μια διεπαφή σήμανσης που οι κλάσεις σας πρέπει να υλοποιούν αν θέλουν να **σειριοποιηθούν** και **αποσειριοποιηθούν**. Η σειριοποίηση αντικειμένων Java (γραφή) γίνεται με το [ObjectOutputStream](http://tutorials.jenkov.com/java-io/objectoutputstream.html) και η αποσειριοποίηση (ανάγνωση) γίνεται με το [ObjectInputStream](http://tutorials.jenkov.com/java-io/objectinputstream.html). +Η διεπαφή Java `Serializable` (`java.io.Serializable`) είναι μια διεπαφή σήμανσης που οι κλάσεις σας πρέπει να υλοποιούν αν θέλουν να είναι **serializable** και **deserializable**. Η σειριοποίηση αντικειμένων Java (γραφή) γίνεται με το [`ObjectOutputStream`](http://tutorials.jenkov.com/java-io/objectoutputstream.html) και η αποσειριοποίηση (ανάγνωση) γίνεται με το [`ObjectInputStream`](http://tutorials.jenkov.com/java-io/objectinputstream.html). -Ας δούμε ένα παράδειγμα με μια **κλάση Person** η οποία είναι **σειριοποιήσιμη**. Αυτή η κλάση **υπερκαλύπτει τη συνάρτηση readObject**, έτσι όταν **οποιοδήποτε αντικείμενο** αυτής της **κλάσης** είναι **αποσειριοποιημένο**, αυτή η **συνάρτηση** θα **εκτελείται**.\ +### Υπενθύμιση: Ποιες μέθοδοι καλούνται έμμεσα κατά την αποσειριοποίηση; + +1. `readObject()` – λογική ανάγνωσης συγκεκριμένης κλάσης (αν έχει υλοποιηθεί και είναι *ιδιωτική*). +2. `readResolve()` – μπορεί να αντικαταστήσει το αποσειριοποιημένο αντικείμενο με ένα άλλο. +3. `validateObject()` – μέσω callbacks `ObjectInputValidation`. +4. `readExternal()` – για κλάσεις που υλοποιούν `Externalizable`. +5. Οι κατασκευαστές **δεν** εκτελούνται – επομένως οι αλυσίδες gadget βασίζονται αποκλειστικά στους προηγούμενους callbacks. + +Οποιαδήποτε μέθοδος σε αυτή την αλυσίδα που καταλήγει να καλεί δεδομένα ελεγχόμενα από επιτιθέμενο (εκτέλεση εντολών, αναζητήσεις JNDI, ανακλαστικότητα, κ.λπ.) μετατρέπει τη ρουτίνα αποσειριοποίησης σε gadget RCE. + +Ας δούμε ένα παράδειγμα με μια **κλάση Person** που είναι **serializable**. Αυτή η κλάση **υπερκαλύπτει τη συνάρτηση readObject**, έτσι όταν **οποιοδήποτε αντικείμενο** αυτής της **κλάσης** είναι **deserialized** αυτή η **συνάρτηση** θα **εκτελείται**.\ Στο παράδειγμα, η **συνάρτηση readObject** της κλάσης Person καλεί τη συνάρτηση `eat()` του κατοικίδιου του και η συνάρτηση `eat()` ενός Σκύλου (για κάποιο λόγο) καλεί ένα **calc.exe**. **Θα δούμε πώς να σειριοποιήσουμε και να αποσειριοποιήσουμε ένα αντικείμενο Person για να εκτελέσουμε αυτόν τον υπολογιστή:** -**Το παρακάτω παράδειγμα είναι από [https://medium.com/@knownsec404team/java-deserialization-tool-gadgetinspector-first-glimpse-74e99e493649](https://medium.com/@knownsec404team/java-deserialization-tool-gadgetinspector-first-glimpse-74e99e493649)** +**Το παρακάτω παράδειγμα είναι από ** ```java import java.io.Serializable; import java.io.*; @@ -80,8 +92,63 @@ payloadTest("test.ser"); } } ``` -## Συμπέρασμα +### Συμπέρασμα (κλασικό σενάριο) -Όπως μπορείτε να δείτε σε αυτό το πολύ βασικό παράδειγμα, η "ευπάθεια" εδώ εμφανίζεται επειδή η **readObject** συνάρτηση **καλεί άλλες ευάλωτες συναρτήσεις**. +Όπως μπορείτε να δείτε σε αυτό το πολύ βασικό παράδειγμα, η “ευπάθεια” εδώ εμφανίζεται επειδή η μέθοδος **readObject()** **καλεί άλλον κώδικα που ελέγχεται από τον επιτιθέμενο**. Σε πραγματικές αλυσίδες gadget, χιλιάδες κλάσεις που περιέχονται σε εξωτερικές βιβλιοθήκες (Commons-Collections, Spring, Groovy, Rome, SnakeYAML, κ.λπ.) μπορούν να καταχραστούν – ο επιτιθέμενος χρειάζεται μόνο *μία* προσβάσιμη gadget για να αποκτήσει εκτέλεση κώδικα. + +--- + +## 2023-2025: Τι νέο υπάρχει στις επιθέσεις αποσυμπίεσης Java; + +* 2023 – CVE-2023-34040: Η αποσυμπίεση κεφαλίδων σφαλμάτων του Spring-Kafka όταν είναι ενεργοποιημένες οι σημαίες `checkDeserExWhen*` επέτρεψε την αυθαίρετη κατασκευή gadget από θέματα που δημοσιεύθηκαν από τον επιτιθέμενο. Διορθώθηκε στην 3.0.10 / 2.9.11. ¹ +* 2023 – CVE-2023-36480: Η υπόθεση αξιόπιστου διακομιστή του Aerospike Java client παραβιάστηκε – οι κακόβουλες απαντήσεις του διακομιστή περιείχαν σειριακά payloads που αποσυμπιέστηκαν από τον client → RCE. ² +* 2023 – CVE-2023-25581: Η ανάλυση του χαρακτηριστικού προφίλ χρήστη του `pac4j-core` αποδέχθηκε blobs Base64 με πρόθεμα `{#sb64}` και τα αποσυμπίεσε παρά την ύπαρξη ενός `RestrictedObjectInputStream`. Αναβάθμιση ≥ 4.0.0. +* 2023 – CVE-2023-4528: Η υπηρεσία JSCAPE MFT Manager (θύρα 10880) αποδέχθηκε Java αντικείμενα κωδικοποιημένα σε XML που οδήγησαν σε RCE ως root/SYSTEM. +* 2024 – Προστέθηκαν πολλές νέες αλυσίδες gadget στο ysoserial-plus(mod) συμπεριλαμβανομένων των κλάσεων Hibernate5, TomcatEmbed και SnakeYAML 2.x που παρακάμπτουν ορισμένα παλιά φίλτρα. + +## Σύγχρονες μετρήσεις που πρέπει να εφαρμόσετε + +1. **JEP 290 / Φιλτράρισμα Σειριοποίησης (Java 9+)** +*Προσθέστε μια λίστα επιτρεπόμενων ή απαγορευμένων κλάσεων:* +```bash +# Αποδεχθείτε μόνο τα DTO σας και το java.base, απορρίψτε τα πάντα τα άλλα +-Djdk.serialFilter="com.example.dto.*;java.base/*;!*" +``` +Προγραμματιστικό παράδειγμα: +```java +var filter = ObjectInputFilter.Config.createFilter("com.example.dto.*;java.base/*;!*" ); +ObjectInputFilter.Config.setSerialFilter(filter); +``` +2. **JEP 415 (Java 17+) Φίλτρα Ειδικών Συγκείμενων** – χρησιμοποιήστε έναν `BinaryOperator` για να εφαρμόσετε διαφορετικά φίλτρα ανά εκτελεστικό συγκείμενο (π.χ., ανά κλήση RMI, ανά καταναλωτή ουράς μηνυμάτων). +3. **Μην εκθέτετε το raw `ObjectInputStream` μέσω του δικτύου** – προτιμήστε κωδικοποιήσεις JSON/Binary χωρίς σημασιολογία εκτέλεσης κώδικα (Jackson μετά την απενεργοποίηση του `DefaultTyping`, Protobuf, Avro, κ.λπ.). +4. **Περιορισμοί Άμυνας σε Βάθος** – Ορίστε μέγιστο μήκος πίνακα, βάθος, αναφορές: +```bash +-Djdk.serialFilter="maxbytes=16384;maxdepth=5;maxrefs=1000" +``` +5. **Συνεχής σάρωση gadget** – εκτελέστε εργαλεία όπως `gadget-inspector` ή `serialpwn-cli` στο CI σας για να αποτύχει η κατασκευή αν γίνει προσβάσιμο ένα επικίνδυνο gadget. + +## Ενημερωμένο cheat-sheet εργαλείων (2024) + +* `ysoserial-plus.jar` – κοινότητα fork με > 130 αλυσίδες gadget: +```bash +java -jar ysoserial-plus.jar CommonsCollections6 'calc' | base64 -w0 +``` +* `marshalsec` – παραμένει η αναφορά για τη δημιουργία gadget JNDI (LDAP/RMI). +* `gadget-probe` – γρήγορη ανακάλυψη gadget black-box κατά των δικτυακών υπηρεσιών. +* `SerialSniffer` – JVMTI agent που εκτυπώνει κάθε κλάση που διαβάζεται από το `ObjectInputStream` (χρήσιμο για τη δημιουργία φίλτρων). +* **Συμβουλή ανίχνευσης** – ενεργοποιήστε το `-Djdk.serialDebug=true` (JDK 22+) για να καταγράψετε τις αποφάσεις φίλτρου και τις απορριφθείσες κλάσεις. + +## Γρήγορη λίστα ελέγχου για ασφαλείς υλοποιήσεις `readObject()` + +1. Κάντε τη μέθοδο `private` και προσθέστε την αναγνώριση `@Serial` (βοηθά στην στατική ανάλυση). +2. Ποτέ μην καλείτε μεθόδους που παρέχονται από τον χρήστη ή μην εκτελείτε I/O στη μέθοδο – μόνο διαβάστε πεδία. +3. Εάν απαιτείται επικύρωση, εκτελέστε την **μετά** την αποσυμπίεση, εκτός της `readObject()`. +4. Προτιμήστε να υλοποιήσετε το `Externalizable` και να κάνετε ρητές αναγνώσεις πεδίων αντί για προεπιλεγμένη σειριοποίηση. +5. Εγγραφείτε σε ένα σκληρυμένο `ObjectInputFilter` ακόμη και για εσωτερικές υπηρεσίες (σχεδίαση ανθεκτική σε παραβιάσεις). + +## Αναφορές + +1. Spring Security Advisory – CVE-2023-34040 Java Deserialization in Spring-Kafka (Αυγ 2023) +2. GitHub Security Lab – GHSL-2023-044: Unsafe Deserialization in Aerospike Java Client (Ιουλ 2023) {{#include ../../banners/hacktricks-training.md}}