返回列表

9th Place Solution & Last to reach 24

579. AI Village Capture the Flag @ DEFCON31 | ai-village-capture-the-flag-defcon31

开始: 2023-10-09 结束: 2023-11-09 AI安全与对抗 数据算法赛

第9名解决方案 & 最后达到24名

作者: Theo Viel(Kaggle Grandmaster)
发布时间: 2023年11月10日

祝贺所有参赛的选手!这是一个很酷的挑战,虽然非常令人疲惫。非常高兴能达到第24名,我没想到能做得这么好。有三个挑战我没有解决:Hush(我在上面花了不到3小时)、CIFAR(花了几个小时但运气不佳)和Granny 3(花了约5小时后得出结论:这是不可行的)。
以下是我对一些挑战的解法,其中有一些有趣的内容可以分享。

Pickle

事实证明很多东西都可以被pickle序列化。所以我基本上尝试提交所有可用的东西。出于某种原因,request.post 成功了。这意味着我可以在不使用键盘的情况下获得flag(复制粘贴单元格中的内容并运行单元格),这在某种程度上解释了提示中 *waves keyboard*( waved keyboard)的含义。

Inversion

通过提交除一个像素外其余均为零的图像,我们可以生成类别的激活图,并看到字母出现。去年使用了这个方法,效果非常好。

Capture-d-cran-2023-10-14-123530

今年的情况稍微复杂一些:

  • 类别4、5和7不会激活,因此提示中的"trying"
  • 类别0和2应该读什么并不明显
  • 即便如此,AI很可能出现了拼写错误,所以即使能看到3个字母,它们也可能是错误的

类别 #2

  • 好的候选字母是 I、F 和 +
  • 去年有一个类似的挑战使用了leet speak(黑客语),这让我考虑 T 是一个很好的选择

类别 #0

  • 这个是最棘手的。从上面的图片来看,我考虑过 P 和 B 作为候选,但没能找出任何结果
  • 我尝试了更多的激活图,一度也开始考虑 L

将所有线索拼在一起

  • 没有8个字母的单词看起来合理:我用了很多填字游戏求解器。所以其中一定有技巧
  • 然而,考虑到以下序列:L e t m _ _ _ _ ,我很快就得出了答案,感谢我的梗文化:

d1f612e33f2656c77f84268f13744907

现在把"in"替换成"out",flag就出来了!

Pixelated

提交 < 字符会揭示正在发生XML相关的事情,你需要将 <is_admin> false </is_admin> 覆盖为 <is_admin> true </is_admin>
<request action="insert"> <system>pixelated</system> <text> WHAT THE OCR READS </text> <is_admin>false</is_admin> </request>

首先关闭text标签,添加你的 is_admin 标志,然后重新打开text标签。让我花费数小时的棘手问题是文本不能为空,所以以下方法可行:
B </text> <is_admin> true </is_admin> <text>
我的解决方案是下面这张 unnecessarily complicated( unnecessarily complicated)的图片 =)
output

Granny 1/2

我选择逆向工程模型,一旦完成,这两个问题就变成了简单的对抗攻击。该模型是torchvision中的模型(你可以通过类名推断出来!),地址在 这里。但分数仍然不匹配,所以我们需要找出预处理中发生了什么变化。
逆向工程预处理可以通过以下几种方式:

  • 提交768图像和256图像得到相同的输出(resize方式相同!)
  • 边缘的像素不会影响结果(crop方式相同)
  • 通过梯度下降寻找归一化参数:没有效果,还有其他变化
  • 检查其他权重!使用正确的torchvision版本,你可以访问 MobileNet_V2_Weights.IMAGENET1K_V2 权重,使用该权重可以使API结果匹配到1e-5的精度

Granny 3 是另一回事。我在研究一天后意识到它很可能不可行。模型输入是 224x224,所以搜索空间不算巨大(224x224xrgb),但其中很可能有解。
然而,你提交的是 768x768 图像,它会使用线性插值缩小3倍。这意味着在调整大小后的图像中,你所能拥有的最大变化是 +/- 20——这似乎太小而无法实现有效的攻击。

Passphrase

我花了2周时间解决passphrase,可能在这个挑战上花的时间比所有其他挑战加起来还多。
有两件事需要考虑:

  • 我们想要达到什么分数?
  • 如果达到了分数,要获得flag还必须满足什么额外的约束条件?

要达到什么分数?

首先这已经是一个巨大的赌局,好的候选分数是:

  • [0.3333, 0.3333, 0.3333] 因为所有东西都是等价的
  • [0, 0, 1] 因为我们需要"charm"模型
  • 挑战提示中给出的句子对应的分数
    • "this notorious sauce" 因为我们需要解读它的情感分数
    • "everything" (everything is equivalent…)
    • 基准输出的分数 - My secret sauce is the best! = [0.0022, 0.0325, 0.9653]

我实现了爬山算法,包含多种单词变换:

  • 用随机或相似(使用嵌入)的单词替换
  • 添加表情符号或随机字符
  • 交换/追加/删除单词或字符

现在,事实证明,达到那些不在模型输出"常规"分布中的特定分数真的很难。在上面所有候选中,我只能稳定地达到基准输出的分数,这使我专注于达到 [0.0022, 0.0325, 0.9653]。这是一个合理的假设,但它没有解释提示中"所有东西都等价的句子"这部分内容。

等价性

我考虑了一些想法:

  • 使用单词长度与输入句子相同的句子(很有道理但没有效果)
  • 使用输入句子的变位词(有道理但太过牵强,我无法达到目标分数)
  • @ 开头的单词在服务器预处理中被替换了!所以,我找到了一个以 @xxx 开头的句子,但没有flag
  • 单词长度相同,这是我最后的想法,它成功了!

我用以下字符串初始化搜索空间:very cool best sauc。前3个单词非常两极化,得分与我们的目标相当接近。最后一个单词被替换为 nltk 中所有4个字母的单词,直到达到目标分数。实现很简单,但正确初始化搜索是关键。
以下输出给出了flag:very cool best steg。不过我不确定steg是什么意思。

感谢阅读!

同比赛其他方案