
AIが出したコラッツ予想の「反証」が3日で無効になるまで
2026年7月25日にAIの助けを借りて作られたコラッツ予想の「反証」が公開されましたが、3日後にはLeanのバグを突いた偽物だとわかりました。偶数なら2で割り奇数なら3倍して1を加える操作を繰り返すと、どの正の整数を出発点にしても必ず1に行き着くというのがコラッツ予想で、反証するには1に行き着かない数が1つでもあることを証明しなければなりません。
2026年7月25日〜28日に発生したこと
- 7/25Ramana Kumar(ラマナ・クマール)氏が、AI支援で作った
sorryなしのコラッツ予想「反証」リポジトリを公開 - 7/28Kiran Gopinathan(キラン・ゴピナタン)氏が、これを
False(偽)を証明できてしまう小さな例にまとめ、不具合報告 #14576を出す - 1時間後Lean側が修正 #14577を反映。Joachim Breitner(ヨアヒム・ブライトナー)氏のレビューを経て本体へ取り込み、修正版を公開
A soundness bug in the Lean kernel ( #14576 ) was reported and fixed during the week of July 27. / On July 25, Ramana Kumar published a repository containing a sorry -free "disproof" of the Collatz conjecture, produced with AI assistance. It is not a valid proof because it exploits a bug in the kernel's handling of nested inductive types. On July 28, Kiran Gopinathan reduced it to a small proof of False and opened issue #14576 . We pushed a fix one hour after the report ( #14577 ). Joachim Breitner reviewed it and suggested improvements, and it was merged. New patch releases are out. — 発生から修正までの経緯に関する記述より公式情報を見る →
「sorryなし」条件の限界
Leanでは証明のまだ埋めていない箇所にsorryという印を置くので、sorryが1つも無いまま検査を通過したリポジトリは、証明が最後まで埋まっていると受け取られがちです。de Moura氏もこのリポジトリを「sorryなし」と紹介したうえで、有効な証明ではないとしています。
ところが今回は検査するプログラムのほうに抜けがあり、チェッカーを通過しても正しい証明にはなっていませんでした。機械検証は人の見落としを防ぐ仕組みですが、チェッカー自体にバグがあれば通ったことは正しさの裏付けになりません。
偽の証明は3日で発覚、カーネルのバグは1時間で修正
公開から3日後の7月28日にはKiran Gopinathan氏が問題の部分だけを取り出してFalse(偽)を証明できてしまう小さな例にまとめ、不具合報告 #14576を出しています。その報告から1時間後に、Lean側は修正 #14577を出し、Joachim Breitner氏のレビューを経て本体へ取り込んだうえで修正版も公開しました。
数学の証明チェッカーの穴は入れ子帰納型の型検査漏れにある
本来は型検査(式の型が合っているかを確認する検査)を受けるはずの部分が、このバグでは検査対象から抜け落ちていました。抜け落ちたのは型の定義には書かれていてもその型の値を作るときの中身には出てこないパラメータで、「ファントムパラメータ」と呼ばれます。
バグ #14576の要点
The bug: when the kernel eliminates a nested occurrence under an inductive type T with parameters Ds , and these parameters are phantom (not mentioned in constructor fields), they disappear from the generated auxiliary type and thus escape type checking. An ill-typed argument in that position could be used to make the kernel accept a proof of False . The bug is only reachable through metaprogramming, by sending the inductive declaration to the kernel directly. The frontend checks the arguments and catches the ill-typed term. This is an implementation bug, not a hole in Lean's meta-theory. — バグの技術的内容、到達経路、および位置づけに関する記述より公式情報を見る →
普通にLeanを書いている人には届かない
このバグを突けるのは、メタプログラミング(プログラムでプログラムを組み立てる書き方)で、帰納型の宣言をカーネルへ直接送信する場合だけです。人がLeanのコードとして書いた場合はカーネルより手前で式を受け取るフロントエンドが引数を検査して、型の合わない項(式のひとかたまり)をその段階で弾きます。
メタプログラミングを禁じても解決しない
議論の中では、カーネルのバグを突いて偽の証明を通す攻撃を防ぐためにメタプログラミングをなくすか制限してはどうか、という案も出ました。ところが、de Moura氏はこの制限案を見当違いだと退けています。
de Moura氏の説明では、エラボレータ(人が書いた式を内部表現へ変換する層)は、そもそも信頼しない前提で作られています。信頼していない部品がおかしな式を作らないことを当てにしていては、証明の正しさを保証できないからです。
不正な証明を通したい人はコンパイルが完了したファイル(.olean)を直接書いたりメモリを書き換えたりして、エラボレータを丸ごと迂回できます。型の合わない宣言は、他の部品に頼らずカーネル自身が拒むしかないとのこと。役割ごとに部品を分けて互いに影響させないこの作りを、de Moura氏は証明項(証明そのものを式で表す仕組み)の大きな利点の1つとしています。
One suggestion in the discussion is to remove or restrict metaprogramming so that this attack is not expressible. This is misguided. The elaborator is untrusted by design. Soundness cannot depend on an untrusted component refusing to build a bad term. An attacker who wants to submit a malicious proof can also write .olean files directly or modify memory, both of which bypass the elaborator entirely. The kernel has to reject ill-typed declarations on its own, in its own process. This separation and isolation of concerns is one of the main advantages of proof terms. — メタプログラミング制限案に対する見解より公式情報を見る →
独立検証器nanodaの古いバージョンでも同じ反証が通る
元のコラッツのリポジトリはLeanとは別に作られた主要な検証器nanoda(ナノダ)でも、1週間前のバージョンでは検査を通過していました。de Moura氏は、Leanとnanodaに互いに無関係なバグが1つずつあったことを意外だったとしています。
2つの実装に別々のバグが重なっていた
| 検証器 | 実装 | 今回の挙動 |
|---|---|---|
| Lean公式カーネル | 参照実装 | 入れ子帰納型の検査が欠けていた |
| nanoda | Chris Bailey氏によるRustの独立実装 | 該当箇所は検査していたが射影(構造から要素を取り出す操作)の型名を確認していなかった |
| lean4lean | 参照実装の移植 | 公式カーネルと同じバグの影響を受ける |
The original Collatz repository also passed a week-old version of nanoda , the main external checker. nanoda is an independent kernel (aka proof/type checker) for Lean implemented in Rust by Chris Bailey . The surprising part is that there are two unrelated bugs involved. The official kernel had a missing check in the nested inductive type support, as explained above. nanoda did check that spot, but did not verify the type name in a projection node. The nanoda bug was reported by Jeremy Chen and fixed a week before the Lean bug was reported. / The practical consequence: checking with an independent kernel still works, since it required two distinct bugs in two implementations, but users who rely on it need current versions of both. / lean4lean is affected by the kernel bug, since its handling of inductives is a port of the reference implementation. — 独立検証器 nanoda がすり抜けた理由、独立カーネルによる検証が依然有効である理由、および lean4lean への影響に関する記述より公式情報を見る →
二重チェックは無効になっていない
別実装の検証器でチェックし直す方法は今も有効です。今回の証明は別々の実装にある無関係な2つのバグの両方を通るように作られていたため、片方にしかバグがなければもう一方の検証器で止まっていたはずです。
ただしこの方法に頼るならLeanと検証器の両方を最新版にしておく必要がある、とde Moura氏は条件を設けています。nanoda側のバグはJeremy Chen氏が報告し、Leanのバグが報告される1週間前に修正されていたとのこと。元のリポジトリを通したのは修正前の古いnanodaでした。
数学の未解決問題への反証が古いnanodaも通った理由は2説ある
nanodaのバグ報告と反証の時期が重なった理由として、当事者はAIが報告を見ていた可能性と、強力なモデルを使うことができるようになったことの2つを考えています。今回の証明は、古いnanodaなら受け入れる式を、Leanのカーネルが一度も検査しない部分に置いていました。
Ramana Kumar氏は時期の重なりを偶然だと考えつつも、証明づくりに使ったAIモデルがnanodaの報告を見ていた可能性は否定できないとしています。一方のJoachim Breitner氏は、このバグを見つけるだけの強力なモデルを使うことができるようになったことに、時期が重なった理由があるのではないかと考えています。
The proof was built so that the expression the kernel never inspects is one that the old nanoda accepted. / Ramana believes the timing was coincidental, but cannot rule out that the model had seen the nanoda report. Joachim proposed the hypothesis that the timing coincidence is due to the availability of strong models able to find this bug. — 証明が狙っていた箇所、および時期の一致についての当事者の見解より公式情報を見る →
バグ発覚後にLean側が変更したこと
ポストモーテムには、Leanの開発組織Lean FROが、このバグを受けて実施した対策も記録されています。その対策として、Lean FROは同じバグの再発を検知するテストを追加したうえで、カーネルの検査そのものも強化しました。
回帰テストとカーネルの追加検査
不正な証明とArthur Adjedj(アルチュール・アジェジ)氏が指摘した関連ケース(非一様パラメータと呼ばれるもの)について、回帰テストがKernel Arenaに入りました。#14582からは入れ子のパラメータについて、型検査を再実行するだけでなくパラメータとして振る舞っているかどうかもカーネルがチェックするようになりました。 カーネルが常に維持すべき前提条件(不変条件)も強化されています。
Regression tests for the exploit, and for a related non-uniform-parameter case raised by Arthur Adjedj, are in the Kernel Arena . / A follow-up PR ( #14582 ) makes the kernel check that the parameters of a nested occurrence actually behave as parameters, rather than only re-type-checking them. / We have also hardened kernel invariants. PRs: #14621 , #14631 , #14632 . — 回帰テスト、追加検査、およびカーネル不変条件の強化に関する記述より公式情報を見る →
OpenAIの協力で見つかった複数のバグ
OpenAIのDaniel Selsam(ダニエル・セルサム)氏はサイバーセキュリティ向けのAIを使ってLean FROに協力し、カーネルからさらに複数の実装ミスを見つけました。見つかったミスはすでにすべて修正済みで、6件の変更として反映されています。
AIが数学の未解決問題に関わった例は、ほかにもあります。87年来のヤコビアン予想に反例が見つかった件です。
8月1日のポストモーテムはこの6件をすべてnanodaが捕まえたと書き、いずれもメタプログラミング経由でしか届かないとしています。8月24日に公開された続報では、6件のうち#14607・#14608・#14609・#14615の4件が健全性バグを修正したものではないとのこと。Lean FROは同じ続報で、別の健全性バグ#14807の偽の証明をnanodaが受理したことも明らかにしています。
nanodaは同じ週に発表されたOpenAI Astraの件でも、証明の第三者チェックに組み込まれています。comparator.liveはnanodaをデフォルトの検証器として使い、上流の修正に遅れないよう更新を毎日追っているとのこと。
Daniel Selsam at OpenAI assisted the Lean FRO with an AI specialized in cybersecurity, and found other programming mistakes in the Lean kernel. All of them have been fixed. All of them were caught by nanoda. These bugs are also only reachable through metaprogramming. PRs: #14607 , #14608 , #14609 , #14613 , #14615 , #14616 . / comparator.live now runs nanoda by default, and nanoda is tracked daily so lean-eval and comparator stay current after upstream fixes. — OpenAI の協力による追加のバグ発見と、検証環境側の更新に関する記述より公式情報を見る →
#14807 fix: make the kernel is_prop check require a sort and #14843 fix: apply #14807 fix to inductive.h. These two PRs fix the implementation of the function that decides whether a type is a proposition. The bogus proof was accepted by nanoda. / The following PRs do not fix soundness bugs. / #14607 fix: missing check_no_metavar_no_fvar checks at inductive.cpp. / #14608 fix: check universe parameters in mutual definitions. / #14609 fix: mark exported stubs of partial definitions as unsafe. / #14615 fix: decide inductive predicates up to universe normalization. — 続報での健全性バグとそうでない修正の区分に関する記述より公式情報を見る →
検証済みカーネルの取り組みはまだ途中
Mario Carneiro(マリオ・カルネイロ)氏のlean4leanはLeanの型理論をLeanで形式化し、カーネルがその理論どおりに実装されていることを証明しようとする取り組みです。ただし、無矛盾性(矛盾を導けないこと)の証明はまだ帰納型を対象に含めておらず、作業は今も続いています。
しかもlean4leanが検証しようとしている実装にも、公式カーネルと同じバグがありました。帰納型部分の検証を仕上げようとした段階でこのバグは見つかっていたはずだ、とde Moura氏は指摘しています。
Mario Carneiro's lean4lean is a Lean formalization of Lean's type theory together with a proof that the kernel implements it. The work is ongoing, the proof of consistency does not cover inductive types yet, and the to-be-verified implementation suffered from the same bug as the official kernel. The bug would have been found when attempting to conclude the verification of this part. — lean4lean による検証の進捗に関する記述より公式情報を見る →
まとめ:形式手法でチェックした定理も検査器の実装しだいで崩れる
機械検証が無意味になったわけではありませんが、そこで得られる保証は検証器のプログラムが正しく作られているかどうかに左右されます。sorryが無ければ証明のすべての段が検査を通ったとは言えても、検査するプログラム自体が正しいかは別にチェックする必要があります。
Leanとは別に作られた検証器でチェックする方法は今も有効で、頼るならLeanと検証器の両方を最新版にする必要があると、de Moura氏はポストモーテムに書いています。今回の証明は別々の実装にある2つのバグがそろって初めて通ったとのこと。nanodaまで通ってしまったのは1週間前の古いバージョンだったためです。
Leanのバグを突いたのもAIなら、別のバグを見つけたのもAIでした。修正の内容は、Leanの公開リポジトリで確認することができます。
FAQ
- AIが作った「コラッツ予想の反証」は本物だったのですか?
- 本物ではありません。Leanの証明チェッカー(カーネル)にあったバグを突いていたため、正しい証明として受理されてしまっただけです。de Moura氏もポストモーテムで、入れ子になった帰納型の処理に関するバグを利用しているので有効な証明ではないと明言しています。
- Leanそのものの理論が間違っていたということですか?
- いいえ。ポストモーテムには、今回の問題が実装上のバグであって、Leanのメタ理論の穴ではないと明記されています。このバグに到達できるのはメタプログラミングで帰納型の宣言をカーネルへ直接送信する経路だけで、通常の書き方であればフロントエンドの検査が型の合わない項を捕まえます。
- 別の検証器で二重チェックすれば防げたのではないですか?
- 今回は防げませんでした。独立実装の検証器nanodaも当時のバージョンでは別のバグを抱えていて、同じ証明を通してしまったためです。それでも2つの実装それぞれに別々のバグが必要だった以上は独立カーネルによる検証は今も有効だ、とポストモーテムは結論づけています。ただし両方を最新版に保つことが条件です。
- メタプログラミングを禁止すれば安全になりますか?
- ポストモーテムはその案を明確に退けています。Leanのエラボレータ(人が書いた式を内部表現へ変換する層)は設計上そもそも信頼されていない、というのが理由です。悪意ある人物はコンパイルが完了したファイルを直接書いたりメモリを書き換えたりしてエラボレータを迂回できるため、カーネルが型の合わない宣言を自力で拒めなければ意味がありません。



