arXiv 上那篇 MACGen,我本来是要划过去的。"安全代码生成"这六个字见太多了——挂个漏洞库、塞进 prompt、指标涨了,收工。结果摘要里一句话把我按住了:
agent 之间不共享完整对话历史。
第一反应:这算什么卖点?后来发现整篇的轴就在这一句上。
先坦白我为什么本来不想看。这类工作的图一画出来基本长这样:生成 → 扫描 → 发现漏洞 → 打补丁 → 再扫。安全是个外挂的检查步骤,挂在最后。这法子当然有效,但它默认了"安全和功能是两件事,先写对再补安全"。我一直觉得这个默认值不对劲,只是没想清楚不对劲在哪。
先别急着往下看。把常见的 multi-agent 摆出来画一张,你就知道开头那句为什么值钱:
规划 ──┐
安全 ──┼──► 共 享 对 话 历 史(所有人都往里灌、也都在读同一坨)
编码 ──┤
审查 ──┘
就一盘。四个角色确实分了工,但大家说的是同一段话,读的也是同一段话。加一个角色,那段对话就长一截;而且每个角色"我是谁、我该管哪一段",会被别人的发言一层一层糊上去。安全顾问开始顺手改代码,编码的人开始替审查者判断安全性——不是他们不听话,是对话里那些东西本来就在那儿摆着,模型看见什么就顺着什么接。
论文用词比我客气,大意是角色边界被稀释、上下文一路膨胀。我说得难听点:那不叫协作,那叫开会。开会能出活,但你得承认它的成本是随人数非线性涨的。
MACGen 干的事,就是把这条总线剪了:
需求 ─► [规划者] ──计划──► [安全顾问] ──CWE 清单+针对性指南──► [编码者] ──代码──► [审查者]
▲ │
└──────────────── 反馈回到编码那一步 ◄──────────────────────────┘
规划者定分步计划;安全顾问指出这次可能踩哪些 CWE,给出针对这个具体任务的写法建议;编码者拿着前面这两样东西写代码;审查者从一个分开的视角给反馈——不是站在编码者刚走过的那条路上回头看。看着就是条普通流水线吧。
关键在箭头里传的东西。传的不是聊天记录,是结构化的产物——上一站写下来的一张单子。下游只读这张单子,读不到上游怎么讨论的、推翻过什么、犹豫过什么。
我看到这儿的时候咔哒一下扣上了 ✨ 剪掉的不是沟通,是沟通的残渣。
打个比方:这像交接班。上一班留给你的不是一段他们干活的录像,是一张填好的表,你拿着表接着干,不需要知道他们为了某个参数吵了几句。
但比喻在这里漏风,得标出来:表不是天上掉下来的。谁定这张表有哪些字段?上游没写进去的东西,下游永远不会知道,包括那些"其实挺重要但没被当成字段"的犹豫。所以这不是把协调成本消掉了,是把"上下文越滚越长"的成本换成了"接口得提前设计好"的成本。挪了个地方,没消失。而且交接班这说法暗示了单向,实际上审查者的反馈要回流到编码那一步,图里那根回头的箭头不能省。
再说个我一开始想岔的地方。
论文把安全代码生成说成多目标优化,我第一遍看觉得这句是凑数的——哪件事不是多目标。但把功能和安全搁进同一句话里想一下,它其实很具体:这两个目标是互相拆台的。为了堵一个边界情况加一层校验,功能行为可能就变了;为了功能跑通把异常吞掉,安全就漏了。所以不是"先写对再补安全",这两件事得同时压着,谁也别把谁带跑。这个我到现在也只明白个大概,可能还有别的意思,先记在这儿。
论文点名的两类老做法我也有体会。一类是往里塞外部安全知识,问题是塞进去的往往是通用建议——注意注入、注意越权——落到这个函数、这条调用路径上,还得模型自己把通用建议翻译成具体写法。翻译这一步没人管,很容易翻车。另一类是让 agent 互相反馈、来回迭代,方向没错,但如果共享同一段对话,就回到上面那盘开会了,转几圈角色糊在一起,上下文还越来越长。
MACGen 把这两条路各掰了一半:安全知识不是塞给编码者的一段话,是安全顾问针对这次任务吐出来的一份指南,"针对性"这一步被单独拎成一个角色来干;迭代反馈保留,但走分离视角,不是同一坨对话。
效果上,作者在 CWEval 和 BaxBench 上测,功能与安全同时达标那个指标(F&S@1)相对直接提示平均涨了 19.61 和 10.57 个百分点。全文 8 页,v3 是 9 月 2 日修完的。8 页。概念本身其实不长,长的是把它画对。
最后推翻一下我自己前面的话。我一开始觉得这篇的核心是"分成四个角色"——多智能体嘛,分工。看完那张图才反应过来,分工这事早就不新鲜了,规划/编码/审查这套组合谁都在用。真正被换掉的是信息通道:从"一条总线所有人共享"换成"每人只读上游那张单子"。角色是表,通道才是里。我第一版画图的时候还画成共享总线了,因为画顺手,手比脑子快。
留个自检:现在你能不能给一个没写过 agent 的人讲清楚,为什么"少给下游一点信息"反而让它更安全?如果讲到一半卡在"那上游漏了怎么办"——恭喜,你卡在了这个方案真正的新成本上,那正是它要付的代价。
下期想画哪个,你说了算。我手上排着 embedding,还有多智能体里那个"什么时候停"的停止条件,哪个先来都行。
