關于管道操作符
windows:
1. “|”:直接執行后面的語句。
2. “||”:如果前面的語句執行失敗,則執行后面的語句,前面的語句只能為假才行。
3. “&”:兩條命令都執行,如果前面的語句為假則直接執行后面的語句,前面的語句可真可假。
4. “&&”:如果前面的語句為假則直接出錯,也不執行后面的語句,前面的語句為真則兩條命令都執行,前面的語句只能為真。linux:
1. “;”:執行完前面的語句再執行后面的語句。
2. “|”:顯示后面語句的執行結果。
3. “||”:當前面的語句執行出錯時,執行后面的語句。
4. “&”:兩條命令都執行,如果前面的語句為假則執行執行后面的語句,前面的語句可真可假。
5. “&&”:如果前面的語句為假則直接出錯,也不執行后面的語句,前面的語句為真則兩條命令都執行,前面的語句只能為真。關于轉義字符
?由反斜杠 \ 后面跟一個或多個字符組成,其目的是為了表示那些不能直接輸入或具有特殊含義的字符。使用轉義字符可以明確其表示的是普通字符而不是特殊含義
1.eval執行
開啟環境,得到源碼主要是eval函數
eval函數:將內容轉為php語言進行執行
所以我們就直接傳入參數cmd沒有看到flag,就再往上進行穿越(或者直接進行查看根目錄也可以)
查看到了flag,就去cat這個文件
2文件包含
得到源碼
strpos函數:
strpos()
函數用于查找字符串中某個子字符串的位置。
那么這個代碼就是:檢查是否有get傳參的參數file,查找參數file里是否有字符flag
由于代碼是!strpos所以需要不含flag,如果含就會輸出hacker
include():語句的主要作用是將指定文件的內容插入到當前 PHP 文件中該語句所在的位置,并當作當前文件的一部分來執行。
這里include()函數就提供了文件包含漏洞,文件包含漏洞同時要求那個被包含的文件是用戶通過傳參方式引入的,這個條件我們也滿足了
?那么我們就直接進行get傳參,傳入參數file,訪問shell.txt,然后進入這個文件,看到有一個request傳參“ctfhub”,所以進行傳參查看就好了
php://input
源碼
<?php
if (isset($_GET['file'])) {if ( substr($_GET["file"], 0, 6) === "php://" ) {include($_GET["file"]);} else {echo "Hacker!!!";}
} else {highlight_file(__FILE__);
}
?>
get傳參傳入參數file
且對參數file的前六個字符有限定,必須是“php://”
而且這里已經給了我們phpinfo界面了,我們直接看看
沒有flag直接給出,但是我們傳入php://input就可以執行傳入的php代碼
所以我們抓包去構造文件執行,寫入命令執行的php代碼
然后再進行cat那個flag文件
讀取源代碼
<?php
error_reporting(E_ALL);
if (isset($_GET['file'])) {if ( substr($_GET["file"], 0, 6) === "php://" ) {include($_GET["file"]);} else {echo "Hacker!!!";}
} else {highlight_file(__FILE__);
}
?>
get傳參file,前六字節限定為php://
而且直接告訴了我們flag文件在哪
所以我們就直接去訪問就好
用php偽協議
這樣就得到了一串base64編碼,進行base64解碼就可以了
遠程包含
和php://input類似
看到了flag,就去cat它
命令注入
源碼
<?php$res = FALSE;if (isset($_GET['ip']) && $_GET['ip']) {$cmd = "ping -c 4 {$_GET['ip']}";exec($cmd, $res);
}?>
?get傳參傳入參數ip
ping -c 4
?是一個常見的命令,用于向指定的 IP 地址發送 4 個 ICMP 數據包。
也就是拼接了一個字符串,讓用戶輸入ip就能執行ping命令
exec($cmd, $res);
:
調用?exec
?函數執行存儲在?$cmd
?中的命令。
exec
?函數會執行一個外部命令,并將命令的最后一行輸出存儲在?$res
?數組中。
所以傳入ip地址以及一個命令
用管道符進行分隔,來使后面的可以被執行,因為使用exec函數,那么ls命令可以被執行
過濾cat
源碼
與上一題相似,get傳參傳入參數ip,管道符|直接執行后面的語句,我們隨便用個ip,然后ls查看目錄
看到了flag文件,cat它
但是源碼中正則表達式將cat給過濾掉了,所以我們用tac
tac:從下往上查看
cat:從上往下查看
但是沒看到有flag,我們就看源碼
過濾空格
源碼同樣get傳參,參數ip,正則表達式將空格過濾掉了
所以我們就用同樣的方法查看目錄
看到了flag文件,cat它
但是通常我們cat文件是cat <文件名>
但是這里過濾了空格,用$IFS$4
這樣就可以查看flag文件里
空格過濾繞過:
1、大括號{}:
??? {cat,flag.php}
2、$IFS代替空格:
$IFS$9,${IFS},$IFS這三個都行
??? Linux下有一個特殊的環境變量叫做IFS,叫做內部字段分隔符 (internal field separator)。
??? ?cmd=ls$IFS-I
??? 單純$IFS2,IFS2被bash解釋器當做變量名,輸不出來結果,加一個{}就固定了變量名
??? ?cmd=ls${IFS}-l
??? $IFS$9后面加個$與{}類似,起截斷作用,$9是當前系統shell進程第九個參數持有者始終為空字符串。
??? ?cmd=ls${IFS}$9-l3、重定向字符<,<>
4、%09繞過(相當于Tab鍵)
過濾目錄分隔符
;(命令分隔符): 無論前一個命令 cmd_1 是否成功,都會執行下一個命令 cmd_2。例: echo "Hello"
源碼
<?php$res?=?FALSE;if?(isset($_GET['ip'])?&&?$_GET['ip'])?{$ip?=?$_GET['ip'];$m?=?[];if?(!preg_match_all("/\//",?$ip,?$m))?{$cmd?=?"ping?-c?4?{$ip}";exec($cmd,?$res);}?else?{$res?=?$m;}
}
?>
由于源碼中禁用了分隔符\,所以我們不能直接訪問某文件夾下的文件
但是我們可以進入某文件夾,只要沒有穿越,就可以訪問文件了
所以,我們先查看該級目錄查看得到了一個目錄,有flag,那么我們就進入后并cat這個flag
同樣是沒有直接看到flag,但是可以看到有一條空的數組的顯示,那么就看源碼
過濾運算符
源碼
<?php$res?=?FALSE;if?(isset($_GET['ip'])?&&?$_GET['ip'])?{$ip?=?$_GET['ip'];$m?=?[];if?(!preg_match_all("/(\||\&)/",?$ip,?$m))?{$cmd?=?"ping?-c?4?{$ip}";exec($cmd,?$res);}?else?{$res?=?$m;}
}
?>
看源碼,可以知道被禁用的運算符并不多 ,僅僅只是|和&
也就是說我們還有其他的沒被禁用,比如;
所以我們就利用;來使后面的代碼被執行
綜合練習
源碼
<?php$res = FALSE;if (isset($_GET['ip']) && $_GET['ip']) {$ip = $_GET['ip'];$m = [];if (!preg_match_all("/(\||&|;| |\/|cat|flag|ctfhub)/", $ip, $m)) {$cmd = "ping -c 4 {$ip}";exec($cmd, $res);} else {$res = $m;}
}
?>
?被禁用了| ,\ ,& , 空格 ,/, ; cat ,flag ,ctfhub
管道符|,&,;都被禁用了,但是我們需要考慮用什么去替代他們實現
%0a可以替代管道符
所以得到:
看到了flag所在,我們再去查看一下flag_is_here目錄
用*繞過flag,${IFS}繞過空格
得到了flag所在的文件,再進行cat
但是需要用tac來進行cat的繞過