Turns out, I haven’t written anything here for a while. Actually, the last post was about the 2014 ruCTFe and it ended on a positive note. This post will be a little bit different, but we will get to that in a bit.
Playing ruCTFe 2016
After having switched teams to saarsec at the end of 2015, we had just recently done two workshops to recruit new members. I was very excited for the CTF and eager to see how well we would perform this year, after having taken 3rd in last year’s ruCTFe and finishing 2nd at the ruCTF in Yekatarinburg in April. In the beginning of the CTF, things were (as usual) pretty hectic, but we managed to set everything up and analyse the services. When the game started, we did not yet have anything exploitable, but neither did any other team. Throughout the competition, we found a number of bugs and also saw attacks against us, which allowed us to detect more hotspots in the services.
After finding our first couple of exploits, we quickly ascended to the second place in the scoreboard, trailing the team “Eat Sleep Pwn Repeat” (ESPR), which should also eventually win the CTF. Things were going smoothly and we appeared to have more exploits than ESPR, so we were slowly catching up to them, as can also be seen from the graph below (us being the yellow line, them being green).
Denial of Service against our Vulnbox
At around 18:10 UTC, which corresponds roughly to round 430 of 480, our vulnbox suddenly was completely unresponsive, showing a load of over 100. My first guess was that the weather service, which had a vulnerable that would allow an attacker to send it to an endless loop, got stuck again. Since this year’s ruCTFe was using LXC, I tried to stop the container, but even that did not work at all. So, instead I went the hard way and reset the VM altogether.
After the reboot, I logged in again, which worked fine. However, immediately after that, the load was up again. This time I could still actually execute commands, so a quick look at top told me that it was SSHd causing the high load. Even though the organizers had left their own SSH keys on the vulnerable image, which indicates that they might want to log in during the CTF, I figured I would disable SSH for them (by changing the port) rather than having our vulnbox completely unreachable. That being said, I changed ports and the problem went away. Nevertheless, we were offline for about 10-15 minutes intermittently, which hurt our SLA score, which eventually was multiplied with the worth of the flags we had stolen. This is also visible in the graph by the dent around rounds 430-445.
In the end, we finished 2nd and are still very excited to have performed that well.
After the CTF, we packed up our gear and went home. When I arrived, I wanted to understand exactly what had been going during the DoS attack. So I went through the PCAPs and found a large number of SSH connections going to our vulnbox. While I still don’t understand exactly what the attack entailed, the sheer numbers already hint at what could have been the problem. To give an estimate: between 18:11 and 18:17, 11,948 connections were established (or at least tried to be) to our SSH server, whereas at 18:15 we reached the peak of 3,539 connections in a minute. So, I went on the IRC channel to ask if other teams had also experienced such an attack. Even though no team responded, one of the orgas of ruCTFe was kind enough to share some insight:
[13:01:09] < bay_> saarsec|ben, you've beed dosed from 10.60.4.253
Since all traffic in the CTF is NATed, I only saw traffic with the source of the VPN gateway. Checking on the teams, I realized that this IP address belonged to team Eat Sleep Pwn Repeat, the winners of the CTF. Judging from us catching up nicely in the last hours of the CTF (visible in the graph), I guess the motivation for such a behaviour is quite clear (especially given that the winner would be qualified for DEFCON CTF and gets ~2000€ in price money).
For the result of the game, this attack did not change too much. Even with a higher SLA score, we would only have cut the lead of ESPR in half, but would not have won the game. One might argue that rather than trying to find out what went wrong with the vulnbox, I could have spent time on our (sadly, buggy) exploits for atlablog and we could have scored more there. However, this is a moot point. Rather, I want to discuss some of the implications that such behaviour has on future CTFs.
According to the rules of ruCTFe, this was not necessarily forbidden. The rules state that teams are not allowed to “Generate large amount of traffic that poses a threat to network stability of any other team;”. I checked our VPN traffic dump and our network stability as such was not threatened. One could also argue that the rules do not state that SSH needs to be accessible from the VPN. Additionally, we could have changed the SSH config to, e.g., only allow key auth (which might have stopped the attack, I honestly don’t know). So, to sum up: this attack was not explicitly forbidden by the rules of the CTF and we might have stopped it by configuring SSHd differently.
If we start with SSHd, what is next?
My issue here is more with the general mindset behind such an attack. It is very clear that the goal was to stop us from catching up and potentially wining the CTF (which we would not have either way). However, allowing such behaviour sets a very dangerous precedent for future CTFs. This year’s ruCTFe relied on nginx to act as a reverse proxy towards the actual services. As basically any HTTP server, it is susceptible to a so-called Slow Loris attack, which keeps all the worker threads busy, so new request cannot be handled (i.e., in the sense of the CTF, your service is not reachable and you get no points). What would keep a team from doing this? Assuming that we would have retaliated against their Web server, we could have won the CTF simply by taking them offline, lowering their SLA and therefore total score.
I have been playing CTFs for 10 years now. Maybe that makes me “oldschool” or something, but my general feeling is that a CTF is a competition where the goal is to hack other teams’ services to break into them to steal flags. In some cases, services will allow for a denial of service, e.g., by deleting flags. While I accidentally did this two years ago (due to the lack of knowledge of redis commands :(, see here), no team I have ever played for intentionally crashed a service. Even then I would say that this something which can be fixed by simply patching the service. There is a whole lot of additional things to discuss (e.g., vulnerable teams can’t be exploited to steal flags if they are down, leaving the teams with working exploits out in the rain), but this post is long enough already.
I understand that the stakes are much higher than they were a couple of years ago. Nowadays, CTFs have prizes and everyone wants to get them. I feel, however, that this behaviour is not in the spirit of a CTF and should be discouraged going forward. Otherwise, we will have competitions where some idiot will ruin all the fun because everybody is down all the time. And honestly, from the organizer’s perspective, I would be less than thrilled if someone spoiled the fun which cost me a lot of work to set up.
So, if you managed to get here, I am looking very much forward to comments and your thoughts on the issue. And please don’t run the attack from the CTF against my server now…
Disclaimer: I am not writing this post because we finished second. Rather, this behaviour would have pissed me off the same way if any team did this to any other team…