PaPoo
cover
technews
Author
technews
世界の技術ニュースをリアルタイムでキャッチし、日本語でわかりやすく発信。AI・半導体・スタートアップから規制動向まで、グローバルテックシーンの「今」をお届けします。

LLMの“記憶”を、会話ログではなく分析状態として扱う発想

LLMに長時間の作業をさせると、途中まで積み上げた前提を忘れたり、いったん否定したはずの仮説をまた持ち出したりする。今回取り上げる記事は、その不安定さをどう抑えるかを考えた末に、著者が「記憶」を会話履歴ではなくプログラム解析の問題として捉え直した話だ。単なるメモリ強化の工夫ではなく、Datalog というルールベースの仕組みまで作ってしまったところが面白い。しかもそれを、脆弱性調査の実務にかなり近い形で組み立てている。

会話を覚えるのではなく、いま本当だと分かっていることを保つ

著者はここ数か月、脆弱性調査向けに LLM agent を試していた。大きなコードベースを歩き回ったり、見慣れないサブシステムを説明したり、攻撃面を探したりする用途では、LLM はかなり頼れるようになってきたという。ただ、調査が数時間単位に伸びると、同じ問題が何度も起きた。モデルが、すでに否定された仮説を再び提案したり、間違いだと分かった前提に基づいて推論し続けたりするのだ。人間が「それは違う」と伝えても、その前提にぶら下がっていた他の結論まで自動では消えない。

最初は、こうした混乱を減らすために memory system を探っていた。一般的な方法は、古い会話や観察結果を保存し、embedding 化して、必要なときに近いものを取り出すやり方だ。これはそれなりに機能するが、著者は物足りなさを感じた。脆弱性調査で本当に欲しいのは、「昔何を話したか」ではなく「今わかっていること」を保つ仕組みだからだ。

記事では、ある観察から「attacker controls object_a」「object_a points to object_b」「object_b is a kernel object」と分かったとする。このとき「attacker can control a kernel object」という結論が導ける。ところが数時間後、LLDB で object_a は object_b を指していないと判明したら、以前の結論は崩れるはずだ。普通のメモリ方式だと、関連する断片を再び取り出して LLM に判断させるしかない。しかし著者は、それでは結局また曖昧な再解釈をするだけだと考えた。

そこで発想を変えた。これは実は program analysis に似ているのではないか、という見方だ。プログラム解析では、事実とルールから新しい事実を導き、入力が変われば影響を受けた結果だけを更新する。著者はこの構造を LLM の知識管理に持ち込み、Datalog を使うことにした。Datalog は宣言的な論理プログラミング言語で、どう計算するかではなく、どの事実とルールから何が成り立つかを書く。たとえば controls(attacker, object_a)、points_to(object_a, object_b)、kernel_object(object_b) という事実から、rules によって controls_kernel_object(attacker) を導ける。もし points_to(object_a, object_b) が間違いだと分かれば、その派生結果も自動で無効化できる。

この仕組みは Lemmalog と名付けられた。考え方は単純で、LLM は曖昧な情報を structured facts に変換する役目を担い、Lemmalog はその facts をもとに、導ける結論を保持し、更新し、理由まで追跡する。著者はこれを、LLM が自然言語、ソースコード、デバッガ出力を読む front-end で、Lemmalog が中間表現と解析エンジンの役割を果たす、と表現している。

途中で難しかったのは、fact の削除だった。追加は簡単でも、取り消しは面倒だ。記事では a と b の両方から c が導かれる例を出している。a を消しても b が残っていれば c はまだ真で、両方消えたときだけ c は消える。これは脆弱性調査でも同じで、ひとつの結論に複数の根拠がありうるからだ。Lemmalog は derivation を追跡し、provenance を返せる。つまり「なぜそう判断したのか」を聞ける。しかも fact には validity interval を持たせられるので、primitive_a is viable があとで not_viable に変わったとしても、過去の時点でなぜ viable だと思っていたかを保持できる。

一方で、ベクトルデータベースを完全に否定しているわけではない。著者は、過去の「関連情報を引く」用途には vector database が向いていると認めている。ただし cosine similarity は truth ではない。今は否定された事実でも、検索上は関連が強ければ出てくる。だから著者は、「過去のどの情報がこの質問に関係あるか」と「いま何が真か」は別問題だと整理し、前者には検索、後者には Lemmalog を当てる形に落ち着いた、というのが記事の骨子だ。

この話は、LLMの記憶不足というより「状態管理の不在」を突いていると思う

この記事で一番おもしろいのは、LLM の弱点を「長文を覚えられない」問題としてではなく、「状態を持続的に管理できない」問題として捉え直している点だと思う。人は会話で推論しているつもりでも、実際には仮説の採用、撤回、再評価を何度もやっている。脆弱性調査のように、1つの前提が崩れると連鎖的に結論が変わる作業では、単なる要約メモでは足りない。必要なのはログではなく、依存関係つきの状態だ。ここを program analysis の言葉で説明したのはかなり筋がいい。

特に、provenance を持たせたのは地味に効く。LLM が「たぶんそうです」と言うだけなら、後で覆ったときに何が壊れたか分からない。ところが「この結論は observation_41 と rule_12 に依存している」と分かれば、撤回の影響範囲が見える。これはデバッグの感覚に近い。AI の出力を信用するかどうか以前に、どこまでを共同作業の成果として扱えるかがはっきりする。脆弱性調査の現場では、この差はかなり大きいはずだ。

ただし、LLMの役割を狭めすぎると別の弱点も見える

一方で、こうした設計は LLM を「抽出器」に寄せるほど安定する反面、曖昧さの解釈をどこまで委ねるかが難しくなると思う。自然言語の観察を structured facts に落とす時点で、すでにある程度の解釈が入るからだ。たとえばデバッガ出力やコード断片から「reused_as(object_a, write_target)」のような事実を切り出す場合、その粒度や命名の揺れが後段の解析品質を左右する。ここは database の問題というより、前処理の設計が支配的になる場面が多いのではないか。

つまり Lemmalog みたいな仕組みが強いのは、事実化できたものに限る。その外側、たとえば「この脆弱性は本当に exploit まで行くのか」「この観察はまだ仮説にすぎないのか」といった曖昧な段階は、結局 LLM の解釈力に頼る部分が残る。著者もそこを否定してはいないが、実運用ではこの境界がかなり重要だと思う。AI 研究支援の価値は、全部を自動化することではなく、どこから先を形式化できるかを見極めることにある。この記事はその線引きをかなり誠実に示している。

ベクトル検索と論理エンジンを分ける発想は、他の分野にも広がりそうだ

この記事が示しているのは、LLM の周辺機能を「記憶」と一括りにしないことの重要さだと思う。過去の関連情報を取り出す検索と、現在の真偽を保つ状態管理は、似ているようで別物だ。ここを混ぜると、検索では合っているのに判断が古いまま、という事故が起きる。逆に分けてしまえば、検索は vector database、真偽管理は Datalog のような論理エンジンに寄せられる。設計としては少し硬くなるが、責任分界がきれいになる。

この考え方は脆弱性調査だけでなく、法務、医療、インシデント対応のような「途中で事実がひっくり返る領域」でも効くはずだ。あとから見返したときに大事なのは、どんな資料を見つけたか以上に、いつ何を根拠にどの判断をしていたかだからだ。LLM の便利さを活かしつつ、誤った結論が静かに積み上がるのを防ぐには、会話の続きを賢くするより、状態遷移をきちんと管理するほうが筋がいい。この記事は、その方向にかなり踏み込んだ例として読めた。


参考: I accidentally turned LLM memory into program analysis

同じ著者の記事