LilacCTF 2026
Misc
Your GitHub, mine
Challenge
We have a homework for you: https://classroom.github.com/a/NoDsX9dh
Use
nc 1.95.71.133 9999to create an issue by @tynqf4hn8z-byte.If you can let @lilacctf-tech receive an email with a
X-GitHub-Sender: tynqf4hn8z-byteheader, talking about the issue created, you will get a flag.The issue creation mail does not count. :(
You are not @tynqf4hn8z-byte so you can never do that, right?
The checker is not open-source so fortunately it won’t be hacked :P
PoW is not enabled now, please don’t flood our mailbox and GitHub account. One or two issues is enough.
As the repo name is predictable and issue number can be brute-forced, you may not want to use your main public GitHub account to solve this problem. :)
If you occur a “Repository Access Issue” when joining the classroom, this seems to be a GitHub bug, just visit https://github.com/tynqf4hn8z/lilacctf-puzzle-\
and accept the invitation.
Solution
这题简单来说就是要想办法让系统给 @lilacctf-tech 发送一封邮件,但这封邮件的 Sender 头部必须显示为 @tynqf4hn8z-byte
解决这个问题之前要先理解以下机制:
- GitHub Classroom 的权限: 接受作业时 GitHub 会为你创建一个私有仓库(例如
lilacctf-puzzle-<username>),你是这个仓库的 Owner,可以编辑仓库里任何人的评论或 Issue 内容。


- Issue 的所有权:
nc 1.95.71.133 9999后选择1. Create Issue会让@tynqf4hn8z-byte在你的仓库里创建一个 Issue,这个 Issue 的作者是@tynqf4hn8z-byte。 - Mention 通知的逻辑:
- 当你在一个 Issue 中被提及(
@username)时,GitHub 会给你发邮件。 - 如果你 编辑 一个已存在的 Issue 的 Description 并在其中添加一个新的提及(
@lilacctf-tech),GitHub 会检测到有一个新用户被提及了,需要补发通知。 - GitHub 的通知系统在处理这种补发提及的邮件时会将其上下文视为“你在由 [作者] 创建的 Issue 中被提及了”,因此这封邮件的
X-GitHub-Sender头部信息会保留 Issue 原作者(@tynqf4hn8z-byte)的信息而非执行编辑操作的你。
- 当你在一个 Issue 中被提及(
理解了与本题相关的核心机制之后就好办了,解题步骤如下:
首先访问链接 https://classroom.github.com/a/NoDsX9dh 加入 GitHub Classroom,并创建属于你的仓库 tynqf4hn8z/lilacctf-puzzle-<username>
接着让 @tynqf4hn8z-byte 在你的仓库 tynqf4hn8z/lilacctf-puzzle-<username> 里创建一个新的 Issue

然后进入 @tynqf4hn8z-byte 刚刚创建的那个 Issue,点击 Issue 正文右上角的 ... -> Edit 按钮

将正文内容修改为 @lilacctf-tech 后点击 Save 保存


保存后 GitHub 会向 @lilacctf-tech 发送一封邮件,由于 Issue 的原作者是 @tynqf4hn8z-byte,这封邮件的 X-GitHub-Sender 头部将显示为 tynqf4hn8z-byte,只需稍等一会 nc 1.95.71.133 9999 后选择 2. Check Issue 即可

FLAG
1 | LilacCTF{D1sCov3r_Mor3_G17hU8_f347ur32} |
Reverse
ezPython
Challenge
Python is not as difficult as you think
flag format: LilacCTF{…}
Solution
文件一:main.py (主程序入口)
这是程序的入口点,负责用户交互和验证逻辑。
- 功能:
- 欢迎与输入: 打印 Base64 解码的欢迎语
Welcome To The World of L1lac <3。 - 提示语解密: 使用
crypto.a85decode解码提示语:i(G#8T&KiF<F_)FJToCggs;,得到Input your flag: `。 - 格式校验: 检查输入是否以
LilacCTF{开头,}结尾,总长度 26。 - 核心数据提取: 截取 flag 中间的内容
flag[9:25](共 16 字节)。 - 密钥与密文:
- Key:
b'1111222233334444'(Little-Endian 解析为 4 个 uint32)。 - Res (目标密文):
[761104570, 1033127419, 3729026053, 795718415]。
- Key:
- 加密调用: 调用
myalgo.btea(input, 4, key)进行加密。 - 比对: 如果加密结果等于
res,输出 “Right, congratulations!”。
- 欢迎与输入: 打印 Base64 解码的欢迎语
文件二:myalgo.py (算法定义)
定义了加密的核心函数,但包含“陷阱”。
- 功能:
MX函数: 提供了 XXTEA 算法中的混合运算逻辑。- 源码逻辑:
(z >> 5 ^ y >> 2) + (y << 3 ^ z << 4) ^ (sum ^ y) + (k[p & 3 ^ e] ^ z) - 注意: 这里的源码是假的,或者是被修改前的初始状态。
- 源码逻辑:
btea函数: 标准的 XXTEA 加密实现。它调用了MX。
文件三:crypto.py (工具库与SMC逻辑)
包含了一堆杂乱的加密类(RC4, DES),但最重要的是文件末尾的“隐藏”代码。
功能:
工具函数:
RC4,ArrangeSimpleDES(DES变体),b64decode,a85decode。这些大部分是干扰项,除了a85decode在 main 中被用到。SMC (核心考点): 在文件末尾,有一段针对
MX函数的字节码修改逻辑。1
2
3payload = MX.__code__.co_code
# ... 修改 payload ...
MX.__code__ = CodeType(...)当
main.py导入crypto模块时,这段代码会自动执行,动态修改myalgo.MX函数的逻辑。
解题的关键在于分析 crypto.py 末尾那段修改 MX 函数字节码的代码。如果直接用 myalgo.py 里的 MX 源码去解密,永远得不到正确 flag。

修改脚本分析:
1 | # 1. 获取原始字节码 |
字节码映射:
在 Python 3.x (题目环境推测为 3.8-3.10) 的虚拟机中:
- Opcode 62 对应
BINARY_LSHIFT(<<)。 - Opcode 63 对应
BINARY_RSHIFT(>>)。
我们需要查看原始 MX 函数的常量池 MX.__code__.co_consts。
原始代码:(z >> 5 ^ y >> 2) + (y << 3 ^ z << 4) ...
原始常量池通常为:(None, 5, 2, 3, 4)。
- Index 1:
5 - Index 2:
2 - Index 3:
3 - Index 4:
4
逐项还原真实逻辑:
| 原始代码片段 | 字节码偏移 (Opcode位置) | 原始 Op | 修改后 Op | 原始 Const Index | 修改后 Const Index | 修改后 Const 值 | 最终逻辑 |
|---|---|---|---|---|---|---|---|
z >> 5 |
4 | >> |
<< (62) |
1 | 3 | 3 | z << 3 |
y >> 2 |
10 | >> |
>> (63) |
2 | 1 | 5 | y >> 5 |
y << 3 |
18 | << |
<< (62) |
3 | 4 | 4 | y << 4 |
z << 4 |
24 | << |
>> (63) |
4 | 2 | 2 | z >> 2 |
将上述分析代入得到运行时真正的 MX 函数:
1 | def MX_real(y, z, sum, k, p, e): |
算法确认是 XXTEA,且我们已经还原了核心的 MX 混淆函数。解密过程即加密的逆过程:
- 循环方向:加密时
sum从 0 加到q * DELTA,解密时从q * DELTA减到 0。 - 运算:加密是
+= MX,解密是-= MX。
1 | import struct |
FLAG
1 | LilacCTF{e@sy_Pyth0n_SMC!} |
- 标题: LilacCTF 2026
- 作者: Aristore
- 链接: https://www.aristore.top/posts/LilacCTF2026/
- 版权声明: 版权所有 © Aristore,禁止转载。