Skip to main content
  1. Blogs/

STF 2022 Web: Blogpost 2

·713 words·4 mins

Recently, I participated with 3 other players in the Stack The Flags 2022 CTF. This is for the writeup of the Web challenge Blogpost 2.

Blogpost 2
Look out for my blog posts, again!!

This is a continuation of the challenge from blogpost 1.

What we know from the previous challenge #

This is reference from the previous challenge with similar but different source code. To download the source code for this challenge, please do so here

If you have not taken a look at the previous challenge, feel free to take a look at it here

From the previous challenge, we know that there is a login page with registration capabilities. After we login, we have the ability to create a blog post.

Summary of what we can do.

ButtonWhat it does
ProfileVisit our profile
Create PostCreate a post on the website
SettingsChange the theme of the website
LogoutLogout of the website

I decided to test if the same payload from the previous challenge will work for this challenge as well.

Payload from previous challenge
Payload from previous challenge

CSP Error
CSP Error

After submitting the post, we can now see that there is an error saying that the content violates CSP policies. This will mean that the website is updated with a Content Security Policy.

Before we look at the source code, let us take a look at what is a Content Security Policy.

What is a Content Security Policy? #

A Content Security Policy (CSP) is an added layer of security that helps to detect and mitigate certain types of attacks, including Cross Site Scripting (XSS) and data injection attacks. It acts as an instruction to your browser on valid sources of information.

An analogy will be telling your friend to only accept words from you and not what other people said.

Let us walk through an example.

Content-Security-Policy: default-src 'self'

The Content Security Policy above will only allow the website to load resources from the same origin. Any scripts which are imported from other sources or <script> tags will not be allowed to be executed. This will show up in the form of an error in the console like the one we saw above in this challenge.

Examining the source code #

To be able to launch a Cross Site Scripting attack, we need to see which are the allowed origins for the website.


app.use(function (req, res, next) {
	  "default-src 'self'; script-src 'self' 'unsafe-eval'; style-src-elem 'self'; font-src 'self'; connect-src 'self';"


Although unsafe-eval looks like a bad idea, it is not as bad as it sounds. This means that the function eval can be called. However, without places to include javascript, we are unable to make use of this.

We can see that these are the following origins that allow scripts to be imported.


Finding a suitable payload #

To find a payload that will work, we can make use of the csp-evaluator by google. By copy pasting the CSP from the source code to the website, we can let it judge if there is problems with the current CSP.

CSP Evaluation
CSP Evaluation

From the CSP testing, we can see that there is a warning the endpoint is vulnerable to CSP bypass.

The next step in finding a payload is the search for the CSP bypass payload. We can refer to Content-Security-Policy-CSP-Bypass-Techniques by bhaveshk90

Relevant Part of Github
Relevant Parts of the Repo

By doing a simple Ctrl + F search for cdnjs, we can see that there is a payload that will work for this challenge. Note that the payload makes use of eval so the ‘unsafe-eval’ in the script-src is relevant to this challenge.

After some tweaking for the payload, we manage to get the flag of the admin.

<script src=""></script>
<div ng-app>
  {{'a'.constructor.prototype.charAt=[].join;$eval('x=1} }

This is the final payload that was used to get the flag.

Final Payload
Final Payload

After submitting the payload, we can see that the flag is sent to the webhook.

Webhook Cookie
Cookies Seen on Webhook

Because there is a use of a + at the back of the payload, we see it as an empty space instead. Some guessing was done to get the flag.


STF22{[email protected][email protected]_ar3_de_b35+}

References #