CTF新手必看:5分钟搞懂Base64隐写术(附Python脚本解析)
刚接触CTF竞赛,尤其是MISC(杂项)方向的朋友,常常会在一些看似简单的文本题面前卡壳。你拿到一个.txt文件,里面是一大段Base64编码的字符串,用在线工具解码后,得到的只是一段看似正常的英文段落,反复检查也找不到flag的踪影。这时候,你很可能遇到了Base64隐写术。这种题目在CTF新手区和一些线上赛中颇为常见,它巧妙利用了Base64编码标准中一个不为人注意的“冗余”特性来隐藏信息。对于新手而言,理解其原理并掌握一个现成的脚本,往往就能在几分钟内破解谜题,体验“柳暗花明”的解题快感。这篇文章,我们就来彻底拆解Base64隐写,让你不仅知其然,更能知其所以然,从此面对这类题目不再迷茫。
1. 从Base64编码说起:为什么会有“冗余”?
要理解隐写,必须先透彻理解Base64编码本身。很多人以为Base64只是简单的“字符转换”,其实它的设计精妙之处,恰恰是隐写术得以存在的土壤。
Base64是一种用64个可打印字符(A-Z, a-z, 0-9, +, /)来表示二进制数据的方法。它的核心思想是将每3个字节(24位)的原始数据,重新按6位一组进行划分,得到4组数据,每组用一个Base64字符来表示。因为6位二进制数的范围是0-63,正好对应64个字符。
这里就引出了第一个关键点:填充(Padding)。当原始数据的字节数不是3的倍数时,就需要在末尾补零,使其总位数是24位(即3字节)的倍数。补零后,再进行6位一组的划分和字符映射。为了标记补了多少个零,编码结果末尾会加上一个或两个等号=。
举个例子,字符串"Man"的编码过程如下:
- ASCII:
M(77)a(97)n(110) - 二进制:
010011010110000101101110 - 按6位分组:
010011010110000101101110 - 十进制: 19 22 5 46
- 查表:
TWFu
所以"Man"编码后是"TWFu"。没有等号,因为原始数据正好是3字节。
再看字符串"Ma":
- ASCII:
M(77)a(97) - 二进制:
0100110101100001 - 只有16位,补两个零(一个字节)凑成24位:
010011010110000100000000 - 按6位分组:
010011010110000100000000 - 注意最后一组
000000,它完全是由我们补的零构成的。 - 十进制: 19 22 4 0
- 查表:
TWEA - 因为补了一个字节(8位)的零,所以在末尾加一个
=,最终编码为"TWE="。
注意:这里补的零(
000000)在解码时会被丢弃。解码器看到末尾的=,就知道最后一部分数据是填充的,不予处理。
我们可以用一个简单的表格来总结这种对应关系:
| 原始数据字节数 | 补零位数 | 编码后字符数 | 末尾等号数 |
|---|---|---|---|
| 3 (整除) |

&spm=1001.2101.3001.5002&articleId=153429563&d=1&t=3&u=0901d96f6efb4eaab8eae39c107735a6)
1636

被折叠的 条评论
为什么被折叠?



