XXE in Public Transport Ticketing Mobile APP
This finding was an another private bug bounty program. The scope of the target was a ticketing android app (Prod). This app was a major Public Transport Ticketing app based out of Germany.
After logging into the android app and going through the account settings, I came across a “Change my data” option.

In the next screen, I have to modify my personal data

While saving the data, I found the following request was sent to the server

The request format was like 062.6.26#{some long data}.
This looks interesting. Next, I selected {some long data} and sent it to the decoder. I tried decoding it and found it was base64. The decoded data was an XML as shown in the below image

Great, next I included the following XXE payload
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE aa[<!ELEMENT bb ANY><!ENTITY xxe SYSTEM "file:///etc/passwd">]>
and called the defined entity &xxe;
from the body as shown in the following image:

Now, all that I needed to do was to encode the whole payload back to base64 format.

Finally, I replaced the payload in the original request and forwarded the request to the server. And, bang! I got the content of /etc/passwd

Since the application was using java, you can even list the directories by using the following payload
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE aa[<!ELEMENT bb ANY><!ENTITY xxe SYSTEM "file://">]>

I was mainly looking for SSH private keys but out of curiosity, I tried to fetch /etc/shadow
(feeling lucky :D). And, to my surprise, I got it (this is a rare case). The response makes it clear that it’s running as root.

I also found, the SSH private keys are too available in the /home/user/.ssh/
directory. This means we can also perform a full RCE on the system but full escalation wasn’t allowed in the program. So I didn’t attempt that and stopped my testing till here and reported the same.

That’s it for now. See you in the next article. Stay Curious ✌🏻
Thank you Bhavuk Jain , Kainat Kamal and jinen for proofreading.