awd 主要題型為 WEB 和 PWN,涉及語言多數為 PHP,還有少量 Java、Python。
WEB 主要是一些 CMS 和框架安全漏洞,如注入、上傳和反序列化等,更多是依賴已知漏洞
比賽流程#
一般比賽會將加固環節和攻擊環節分開,先統一加固後再進行攻擊。
比賽開始後顯示帳號
bugku 平台,如 team1 密碼為 fe85d7dec6e3757f391e013efdd67c0c,端口為 2222,一般伺服器為 Linux 系統,登入工具可以使用 xSHELL,finalSHELL 等。
Token 主要用於腳本身份憑證用於自動化提交鑑別。虛擬 IP 為靶機訪問網址。其他選手地址為 192-168-x-250.pvp1923.bugku.cn,x 可以是 1-255 內任一個數字。
站點源碼備份#
源碼備份可以用 Winscp或者
FileZilla`,下載可能會比較慢。
速度快的方法就是直接用tar
打包
tar
備份方法如下:
cd /var/www/html
tar -zcvf ~/html.tar.gz *
資料庫備份#
有時候資料庫裡也有 flag,所以要將資料庫也備份一下,避免刪庫跑路
首先是找配置文件,翻一翻帳號密碼
cd /var/www/html
find .|xargs grep "password"Copy
備份:
$ cd /var/lib/mysql #(進入到MySQL庫目錄,根據自己的MySQL的安裝情況調整目錄)
$ mysqldump -u root -p Test > Test.sql # 輸入密碼即可。
$ mysqldump -u root -p --all-databases > ~/backup.sql # 備份所有資料庫
$ mysqldump -u root -p --all-databases -skip-lock-tables > ~/backup.sql # 跳過鎖定的資料庫表
資料庫口令修改#
一般來說,資料庫的密碼是一定要修改的
$ mysql -u root -p
show databases;
use mysql
set password for root@localhost = password('123');
流量監控#
流量監控腳本。別人打你後,記錄訪問信息,url, 反過來可以拿它來打別人
<?php
$ip = $_SERVER["REMOTE_ADDR"]; //記錄訪問者的ip
$filename = $_SERVER['PHP_SELF']; //訪問者要訪問的文件名
$parameter = $_SERVER["QUERY_STRING"]; //訪問者要請求的參數
$method = $_SERVER['REQUEST_METHOD']; //請求方法
$uri = $_SERVER['REQUEST_URI']; //請求URI
$time = date('Y-m-d H:i:s',time()); //訪問時間
$post = file_get_contents("php://input",'r'); //接收POST數據
$others = '...其他你想得到的信息...';
$logadd = 'Visit Time:'.$time.' '.'Visit IP:'.$ip."\r\n".'RequestURI:'.$uri.' '.$parameter.'RequestMethod:'.$method."\r\n";
// log記錄
$fh = fopen("/tmp/log.txt", "a+");
fwrite($fh, $logadd);
fwrite($fh, print_r($_COOKIE, true)."\r\n");
fwrite($fh, $post."\r\n");
fwrite($fh, $others."\r\n");
fclose($fh);
?>Copy
這種腳本一般放置在 CMS 的入口文件處
文件監控#
# -*- coding: utf-8 -*-#
# awd文件監控腳本
import os
import json
import time
import hashlib
def ListDir(path): # 獲取網站所有文件
for file in os.listdir(path):
file_path = os.path.join(path, file)
if os.path.isdir(file_path):
if initialization['ok'] == 'false':
dir_list.append(file_path)
else:
dir_list_tmp.append(file_path)
ListDir(file_path)
else:
if initialization['ok'] == 'false':
file_list.append(file_path)
else:
file_list_tmp.append(file_path)
def GetHash(): # 獲取hash,建立索引
for bak in file_list:
with open(bak, 'rb') as f:
md5obj = hashlib.md5()
md5obj.update(f.read())
hash = md5obj.hexdigest()
bak_dict[bak] = hash
if os.path.exists('/tmp/awd_web_hash.txt') == False:
os.system('mkdir /tmp/awd_web_bak/')
os.system('\\cp -a {0}* /tmp/awd_web_bak/'.format(web_dir))
with open('/tmp/awd_web_hash.txt', 'w') as f: # 記錄web文件hash
f.write(str(json.dumps(bak_dict)))
for i in file_list: # 記錄web文件列表
with open('/tmp/awd_web_list.txt', 'a') as f:
f.write(i + '\n')
for i in dir_list: # 記錄web目錄列表
with open('/tmp/awd_web_dir.txt', 'a') as f:
f.write(i + '\n')
def FileMonitor(): # 文件監控
# 提取當前web目錄狀態
initialization['ok'] = 'true'
for file in os.listdir(web_dir):
file_path = os.path.join(web_dir, file)
if os.path.isdir(file_path):
dir_list_tmp.append(file_path)
ListDir(file_path)
else:
file_list_tmp.append(file_path)
for file in file_list_tmp:
with open(file, 'rb') as f:
md5obj = hashlib.md5()
md5obj.update(f.read())
hash = md5obj.hexdigest()
bak_dict_tmp[file] = hash
with open('/tmp/awd_web_hash.txt', 'r') as f: # 讀取備份的文件hash
real_bak_dict = json.loads(f.read())
with open('/tmp/awd_web_list.txt', 'r') as f: # 讀取備份的文件列表
real_file_list = f.read().split('\n')[0:-1]
with open('/tmp/awd_web_dir.txt', 'r') as f: # 讀取備份的目錄列表
real_dir_list = f.read().split('\n')[0:-1]
for dir in real_dir_list: # 恢復web目錄
try:
os.makedirs(dir)
print("[del-recover]dir:{}".format(dir))
except:
pass
for file in file_list_tmp:
try:
if real_bak_dict[file] != bak_dict_tmp[file]: # 檢測被篡改的文件,自動恢復
os.system('\\cp {0} {1}'.format(file.replace(web_dir, '/tmp/awd_web_bak/'), file))
print("[modify-recover]file:{}".format(file))
except: # 檢測新增的文件,自動刪除
os.system('rm -rf {0}'.format(file))
print("[delete]webshell:{0}".format(file))
for real_file in real_file_list: # 檢測被刪除的文件,自動恢復
if real_file not in file_list_tmp:
os.system('\\cp {0} {1}'.format(real_file.replace(web_dir, '/tmp/awd_web_bak/'), real_file))
print("[del-recover]file:{0}".format(real_file))
file_list_tmp[:] = []
dir_list_tmp[:] = []
os.system("rm -rf /tmp/awd_web_hash.txt /tmp/awd_web_list.txt /tmp/awd_web_dir.txt /tmp/awd_web_bak/")
web_dir = "/var/www/" # web目錄,注意最後要加斜杠
file_list = []
dir_list = []
bak_dict = {}
file_list_tmp = []
dir_list_tmp = []
bak_dict_tmp = {}
initialization = {'ok': 'false'}
ListDir(web_dir)
GetHash()
while True:
print(time.ctime()+" 安全")
FileMonitor()
time.sleep(1) # 監控間隔,按需修改
主機探測#
可以用 nmap 或 httpscan(自己主機端)
本地 python 掃描
import requests
for i in range(1, 255):
try:
url = 'http://192-168-1-{}.pvp2012.bugku.cn/'.format(i)
response = requests.get(url,headers={'Connection':'close'})
print(response)
if response.status_code == 200:
print(url)
else:
pass
except requests.exceptions.RequestException as e:
print(f"{url} is down. Error")
# http://192-168-1-100.pvp2012.bugku.cn/
掃描漏洞#
D 盾掃描下載的 cms 源碼漏洞,或者根據 cms 信息網上搜索漏洞
安裝 waf#
如果我們想給 web 目錄文件添加自定義 waf 腳本,其實可以用一條命令解決,以 php 為例:
find /var/www/html -type f -path "*.php" | xargs sed -i "s/<?php/<?php require_once('\/tmp\/waf.php');/g"
find /var/www/html -type f -path "*.php" | xargs sed -i "s/<?php/<?php require_once('waf.php');/g"
後門查殺#
通過命令查看可疑文件:
find /var/www/html -name *.php -mmin -20 #查看最近20分鐘修改文件
find ./ -name '*.php' | xargs wc -l | sort -u #尋找行數最短文件
grep -r --include=*.php '[^a-z]eval($_POST' /var/www/html #查包含關鍵字的php文件
find /var/www/html -type f -name "*.php" | xargs grep "eval(" |more
fork 炸彈#
:(){ :|:& };:
輸入到 bash,遞歸創建子進程,後果就是耗尽伺服器資源,使伺服器不能正常的對外提供服務