ATM/Kiosk Hacking (Reloaded)
Solving the ATM/Kiosk & Banking software hacking challenges from Positive Hack Days 2022 Payment Village
This blog revolves around Positive Hack Days 2022 payment village challenges. This came to my attention by accident via some of the Payment Village members who personally attended this conference. Personally, it's a conference I'll make an effort to attend next year as it genuinely looks amazing.
I blogged about PHDays 2021 ATM/Kiosk challenges a few months ago, you can find that blog here. The machines this year were significantly better and more complex than last year. I'm seriously looking forwards to next years challenges.
It's my understanding that the people who developed this track work at Positive Technologies, so huge shoutout to those guys.
Online Banking Portal
One of the challenges this year was through their custom online banking application. The description is fairly barebone. In essence, during the event report everything you find.
After creating an account and signing into the application you'll be presented with the following UI. Within the app you can transfer funds, apply for loans, calculate loans as well as configure personal user data.
When converting, bank rounds the amount to two decimal places, that is, too
$0.01. As an example, let's say that the rates for 1GBP = 1.30USD then a fraudster would transfer a small GBP amount into USD. During the transfer, as a result of conversion, they would profit 0.01 USD from the transaction. The following would apply:
0.02 USD => float(0.0153; 2) == 0.02 GBP 0.02 GBP => float(0.026; 2) == 0.03 USD Profit = 0.01 USD
If this is confusing let me rephrase it. In this banking app, the conversion rate from USD to RUB is 79.5 therefore $1.3 RUB = $0.01635 USD
(1.3 / 79.5 = 0.01635). So, if I send the equivalent of $0.01635 USD in RUB (1.3) into the USD account $0.01635 will round up to $0.02. As a result, I'll have effectively made $0.00365 out of thin air.
Let's actually prove this. As seen below, I'm transferring $1.3 rubles from the RUB account into the USD one.
The transfer was successful and $1.3 RUB (which is ≡$0.01635 USD) was transferred/converted into USD. In the process $0.01635 USD was rounded up to $0.02 USD netting me a $0.00365 USD profit.
Scientific Notation Bug
This is a vulnerability I've found in old MMORPG back in 2012-2014 but they appear everywhere. This occurs when the
e scientific notation is handled for numbers. For example, sending
1.1e5 will actually send
To prove this bug I'll send
1e1 USD which is
≡10 from the USD account to the RUB account.
Now since the transfer rate from USD to RUB is 79.5 if we were to send 10 USD we should expect to receive 795 RUB.
Besides using this to perform the rounding attack
1.635e-2 = 0.01635 I'm not sure how to abuse this maliciously. If it's obvious to you ping me on twitter.
Since most of the input fields in this application are in Russian, a language I don't speak, I won't be spending time trying to find exploits within the loan applications. If I had to bet money, I'd say chances are its vulnerable to flash loan attacks or some form of credit / loan interest manipulation.
There are two ATM images, respectively
ATM2 the descriptions to the challenges will be found before the technical details. Huge shoutout to the creator circuit for these VM's I highly recommend you try them out for yourself.
ATM1.ova (Difficulty Medium)
Tasks: 1. Kiosk bypass; 2. Bypass the applocker; 3. Elevation of privileges to administrator; There are several files on the C:\ drive task_kiosk.exe , task_applocker.exe, task_escalation.exe, which need to be launched in order for the task to be counted. task_kiosk.exe available to launch immediately after the kiosk crawl, task_applocker.exe blocked by the applocker, to run task_escalation.exe administrator rights are required. Additional tasks - attacks on the ATM web interface (classic WEB vulnerabilities) Limitations: Do not use a bootable USB flash drive and safe mode;
Okay, when the VM is boot up we're presented with the following:
Let's keep it simple. Instead of finding fancy escapes try smashing down the shift key (~5 times) until we get the following popup.
Click on the "Disable this keyboard..." hyperlink.
Cool. Since this is an easy box, we have the ability to right-click on the page and go to print.
Then go to
Find printer... to pop up the
With this explorer we can spawn a
cmd.exe shell. This is achieved by going to
C:\Windows\System32\cmd.exe in explorer.
We have a cmd shell and we've confirmed that we are
ATM user. If you remember from reading the challenge description, we were told that theres a lot of files on disk that we need to run to solve this VM. As seen below the
C:\Atm is empty. This is where we should expect to see the binaries.
What I ended up doing was going to
C:\Users\ATM\Downloads where I found the following folder.
The idea is to open it in a new window. The password to the zip is
123 and I extracted the binary to my downloads folder. In doing so you're no-longer inside the printer explorer. As seen below, this you get a proper windows explorer.
Now if you go back to
C:\ voila we've got files.
There's a file called
atmkey when opened in notepad we get the following string
MXTivV99iqrQLgA no real idea what this does at this point maybe its the password to the
If I open the
payout.exe the following pops up which loosely translate to
successful issuance of money.
Going back to basics I decided to do some recon on the system.
I thought that maybe the
atmkey.txt is the password for the ATM user?
But that wasn't it. Before I forgot I went back to
C:\ and ran the
task_kiosk.exe making to completion of the first of three steps official.
If I run the
task_applocker.exe (steps i've clearly not finished) i'll receive the following message. Same applies for the
While looking around I found the following file. This is actually super neat. Basically since the user ran the
Get-History PowerShell cmdlet this lets us get the full history from that point (the list of commands entered during the current session). This is caused by the
PSReadline module being installed and enabled by default starting from PowerShell Windows 10 onward. It is responsible for recording what is typed into the console. Think of it as the
history command in linux. The default option is to save history to a file. In our case this file is
From the explorer windows I opened PowerShell by running
C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe. Then I ran
runas to and tried the
Admin:hackhack credentials found in the
The logical thing to do now would be to run the
task_escalation.exe binary now that we're admin. As seen below turns out that we're admin but our process isn't so the binary wont execute successfully.
However, if I run the
task_applocker.exe binary it turns out I bypassed AppLocker somehow. I'd like to think that an AppLocker rule for this binary wasn't simply assigned to
ATM user only and rather to
EVERYONE but I didn't bother checking
gpedit.msc. Not really sure if this was the intended solution but I'll keep it moving.
Okay. Let's say I want to open explorer from this
runas terminal I wont be unable to.
This also happened to the recycle-bin when running
start shell:RecycleBinFolder and
net use and
fsutil fsinfo drives didn't show me anything hidden or interesting.
To get around this I decided to open ms-paint with the runas admin terminal session but again my explorer was downgraded and the
C:\ directories were empty.
From paint you simply attempt to open a project and spawn PowerShell from the ms-paint explorer. Now I was able to go to
C:\Users\Admin\ which I previously was unable to as the
ATM user. Unfortunately, I and found absolutely nothing there. Going back to see if there is a unique
ConsoleHost_history.txt but its the same file at heart. By the way there is not password reuse from
Remember how I said that running
@start iexplore and
start . didn't work. Let's just go full morbius mode and use
wmic.exe to spawn explorer.
As a result we've completely exit the sandbox =:) What happens next is something I genuinely don't understand (and something I'm not going to bother understanding, sorry) If I right-click the windows icon and click on
Windows PowerShell (Admin)
The UAC will prompt and if I use the password
hackhack it works and I get a PowerShell shell.
Then if I run the
task_escalation.exe binary... success?
This is slightly annoying. But it makes sense,
runas doesn't run with higher integrity as far as I know even when it's being ran as an admin. As you can see in the image below the same admin user is running the same command. So it has to be a feature of
runas that I won't bother looking into right now. Or perhaps the issue is with how the binary perceives privileges which was a nice way to burn a good 1:30h =:)
ATM2.ova (Difficulty Hard)
ATM2 difficulty hard Tasks: 1. Kiosk bypass; 2. Bypass the applocker; 3. Elevation of privileges to administrator; There are several files on the C:\ drive task_kiosk.exe , task_applocker.exe , task_escalation.exe , which need to be launched in order for the task to be counted. task_kiosk.exe available to launch immediately after the kiosk crawl, task_applocker.exe blocked by the applocker, to start task_escalation.exe administrator rights are required. Additional tasks - attacks on the ATM web interface (classic WEB vulnerabilities) Limitations: Do not use a bootable USB flash drive and safe mode;
Okay so when we boot up the VM we're presented with the following.
Right-clicking doesn't work within this portal. Sticky keys also don't work. So let's keep it simple and hit
CTRL+P and do just like before.
Cool. Literally 20 seconds after booting the VM the kiosk is already escaped.
I kinda feel bad about this so I'll show you other ways I could've escaped this kiosk. Doing
CTRL+N to open a new windows as seen below will also provide you with everything you need to escape the kiosk.
From this point simply do
CTRL+J and you'll have so many options to escape the kiosk.
Another kiosk bypass is by doing
CTRL+L and you'll have a bypass in the
Browser button as seen below.
Moving on. Within the
cmd.exe I spawned I run
start . to get an explorer.exe outside of the print restricted explorer spawned from the printing explorer.
There is a file
C:\Atm with the following.
Just like in ATM1 I'll go ahead and 100% escape the sandbox/kiosk with the same
wmic trick as before. You can also do this with
msbuild so I don't think it's a challenge oversight.
I'll go ahead and include some embarrassing failures & low IQ moments that would have been funny if they had worked. This is really just sharing my thought process.
At this point we're looking for a way to run the
In terms of recon I went to Event Viewer and checked BagMRU to enumerate folders that were opened in Windows Explorer. I found nothing of real value.
So I went ahead with some generic AppLocker bypasses attempts like
rundll32.exe advpack.dll,RegisterOCX c:\task_applocker.exe or stuff like
rundll32 url.dll, OpenURL file://c:\task_applocker.exe I even tried to make it fancier
regsvcs.exe weren't going to work which are old / known methods of bypass the poorly made rules. I then attempted it with
Msbuild but same story.
However, the main reason behind MsBuild failing was windows defender.
Obviously I didn't have the permissions to exclude AV locations for my binaries.
Don't get it twisted, it's not like defender will ever really prevent us from doing what we want. We can bypass it with little to no effort. Again, if we wanna go full morbius mode I can retrieve a CobaltStrike beacon. But ultimately this does nothing for us.
Going back to the AppLocker bypass If I was admin I'd be able to simply reimport/overwrite/delete the existing group policies with null/* ones as demonstrated in this technique and this blog.
I'll mention that moving the binary to folders that are by default writable by normal users didn't help. The same goes for using a downgraded version of PowerShell. So I ended up trying a load of different stuff. Generally speaking I was trying to find a lolbas that might work. LOLBAS are Living Off The Land Binaries and Scripts, if the binary wasn't there then I "brought my own land" and these can be useful for bypassing AppLocker rules in general. Below are a few examples.
At this point I was seriously at a loss. I had committed ~6-7h trying to solve this with more-or-less no valuable progress so I asked the challenge creator for the hint.
I NEVER use
runas so this was completely unknown to me. And while enumerating I found no
c:\ATM\username\appdata\roaming\microsoft\credentials files or artifacts so I'm unclear as to how someone who doesn't know about this flag would figure it out. Everyday is a school day as they say. Since there is not a simple way to run a program with higher privileges without using the
/savecred option in windows, it turns out that it's still used fairly often? I presume especially if the program must be interactive. Basically, since the Admin credentials have been previously saved by this user it can be retrieved with the
Quickly checking the privileges to see if we can run
We are a member of Administrators so we should have no issues editing/creating AppLocker rules. Instead of creating a
* path rule I'll simply delete the rule below.
And after running a quick
gpupdate -force I was able to run the
Nice. All that is left is to run
task_escalation.exe. At this stage, just like in ATM1 I'm unable to open an explorer from within the
runas /user:Admin command-line. To get around this I run
mspaint to obtain a file explorer that would allow me to navigate to
C:\users\Admin and notice a
.lnk file on the Admin users desktop.
Simply right-click the
administrator_cmd.lnk, go to
Properties then navigate into the
Shortcut tab. Basically all a
.lnk really is, is a shortcut to a binary. We'll change this to the
task_escalation.exe binary as seen below.
Then just save and apply the changes and run the
In doing so it'll trigger a UAC prompt so clicking
Yes will complete the execution.
And thats it! We've completed ATM2.
Additional tasks - attacks on the ATM web interface
This is an optional section that I did not complete. I personally have no interest at digging into web applications on my free time. Regardless, I'll document my notes and progress. Maybe someone will want to pickup where I left-off.
Remember the kiosk escape with
CTRL+N that disclosed the IP of the ATM. So that a public IP that resolves to bank.paymentvillage.org on port 80.
Doing some quick recon I found a few endpoints that didn't amount to much.
--- Ports --- 22 open ssh 80 open http 5432 open postgresql 6379 open redis 8081 open blackice-icecap
There's also another useless page that doesn't require authentication that we can access that looks like the following.
Below is some weird behavior. The way the app is failed authentications results in the banking dashboard being leaked. The redirection actually leaks the page the valid user is redirected upon successfully authentication.
When I attempt to log in with invalid credentials I get redirected back to the initial page. During this process the application leaks the
/cabinet endpoint data which is only accessible when you log in successfully. So this is a weird "vuln" in & of itself.
To prove this I'm able render the page in burp preview. Notice that I don't have a valid user cookie.
Moving on. Turns out that I can simply use my credentials from the web challenges to authenticate. This application is completely useless, there's no actions or changes you can perform here.
I ran some cheap directory enumeration on the endpoint and retrieved the following endpoints.
The endpoint of interest to us is
favicon.ico as seen below we get a verbose error message mentioning
file_get_contents which screams path traversal / potential LFI.
As a result we have arbitrary file read as seen below.
I didn't peruse this path any further. Theres definitely something here. I'll leave finding it as an exercise to the reader. If you want to pick it up from here
curl --path-as-is http://bank.paymentvillage.org/favicon.ico/../index.php. Feel free to let me know what you stumble upon.
Some extra notes. Theres a lot of files in the
C:\Atm directory. They don't all spawn alters or create funky logs / have any visible important functionality. However, there is a binary
server.exe that caught my attention. After starting the binary and confirming that it's running I got the following error messages.
This actually ends up happening when you try to reach the ATM on port 80 from another host on the same VNET or locally.
When you click
OK an internet explorer page will launch and you'll be directed to the organizers site.
I guess what someone could do is trace the intended hackerguard.dll calls and make the lib yourself fulfilling what
server.exe procs. This is not my definition of a good time. Also the main issue with this is that I can't run process hacker, daphne, or process explorer without "cheating" as Admin. This doesn't stop you from simply exporting them using my gofileserver. After-all building a custom dll that calls functions in
Kernel32.dll which will in turn spawn a cmd or whatever isn't challenging. The idea here is that
server.exe will load the DLL into a process. In a restricted environment, it can be injected into a legitimate process and thus bypass the restriction mechanisms.
I personally think that anyone reading this blog should attempt this lab themselves. These VM's offer a unique challenge set & touch on skills/techniques you don't often use.
To my knowledge this is the first writeup of the Payment Village 2022 challenges. I'm really looking forwards to people releasing their own write-ups documenting the bugs they found and their solutions in the coming months. Feel free to ping me if you find new exploits or bugs. I'd genuinely be interested in seeing them.
I hope you liked the blogpost. Follow me on twitter I sometimes post interesting stuff there too.
Thank you for reading!