GitLabの脆弱性CVE-2026-97229とは、CI/CDの正規表現でRubyのOnigmoを壊すRCEと修正版
対象の目安: GitLabを自社で運用するインフラ担当 / Rubyアプリの開発者 / 実務


GitLabを自社で運用している組織に向けて、緊急度の高い脆弱性が出ています。CVE-2026-97229は、CI/CDの設定に書かれた正規表現をGitLabが処理するときに、Rubyの正規表現エンジン(Onigmo)の整数オーバーフローを突かれ、GitLabサーバー上で任意のコードを実行される問題です。GitLabは2026年10月12日に修正版を公開し、CISAは10月29日に、実際の悪用を確認した脆弱性のカタログ(KEV)へ追加しました。
原因はGitLab固有のコードではなく、GitLabが使うRubyの正規表現の処理にあります。GitLabは同じ系統の不具合として、ほかに3件のCVEを9月から10月にかけて公開しており、Rubyも10月23日に修正版を出しました。この記事は、GitLabのセルフマネージド版を運用するインフラ担当と、Rubyでアプリを書く開発者に向けて、仕組み、関連するCVE、修正版、点検の手順を、GitLabとRubyの公式発表、CVEレコード、NVD、CISAのKEVで整理します。攻撃を再現する手順は扱いません。事実は執筆時点(2026年11月6日)で確認できた範囲に限ります。
CVE-2026-97229はCI/CDの正規表現を入口にした整数オーバーフロー
CVEレコードの説明によれば、GitLab CE/EEの19.2から19.4の各系列で、CI/CDの設定に書かれた細工した正規表現を通じて、未認証の利用者がGitLabサーバー上で任意のコードを実行できるおそれがありました。原因は正規表現の検証が不十分なことです。CVEの採番機関(CNA)はGitLab自身で、レコードは2026年10月13日(UTC)に公開されました。報告者はHackerOne経由のjoaxcar氏(Johan Carlsson氏)です。
| 項目 | 内容 |
|---|---|
| CVE | CVE-2026-97229 |
| 題名(CNA) | Integer Overflow or Wraparound in GitLab |
| 弱点 | CWE-190(整数オーバーフロー) |
| CVSS v3.1 | 10.0 Critical(AV:N/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:H、GitLabの評価) |
| 影響 | 19.2以上19.2.8未満、19.3以上19.3.5未満、19.4以上19.4.2未満 |
| 修正 | 19.4.2、19.3.5、19.2.8(2026年10月12日) |
| KEV | 2026年10月29日に追加。米国連邦機関の対応期限は11月1日。ランサムウェアでの利用は不明 |
NVDは分析済み(Analyzed)の状態で、CVSSはGitLabの評価を載せています。CISAの補足情報(ADP)にあるSSVCの評価は、悪用(Exploitation)がactive、自動化のしやすさ(Automatable)がyes、技術的な影響(Technical Impact)がtotalです。KEVの項目には、侵害の有無を調べる手順の要求(forensicTriage)が付いており、注記には「同じRubyとOnigmoの整数オーバーフローの影響を、ほかの製品も受ける可能性がある」と書かれています。
GitLab.comとGitLab Dedicatedは、パッチリリースの公開前に修正済みです。対応が必要なのは、自社のサーバーやクラウドで動かしているセルフマネージド版です。
Onigmoの整数オーバーフローがコード実行につながる仕組み
Rubyの正規表現は、Onigmoというエンジンが文字列のパターンを内部の命令列へコンパイルしてから照合します。Rubyの告知によれば、GitLabは「細工したパターンが、Rubyのコンパイル中にメモリを壊せる」ことを見つけました。CVE-2026-97229は、コンパイル後のパターンの大きさを計算する部分の整数オーバーフローで、Rubyの修正番号は#19020です。
GitLabが19.4.2の告知から参照している検知ルールの技術説明によれば、GitLabはCI設定のrules:exists:regexpとrules:changes:regexpに書かれた正規表現を、先読みを使えるようにするためOnigmoで評価しています。Onigmoはコンパイル後の命令列の中のジャンプ先を符号付き32ビットの相対値で表し、命令列全体の大きさに上限を設けていませんでした。Rubyの修正(#19020)の説明によれば、.{100000,}のような繰り返しは10バイトほどの記述から約10万個の命令に展開されるため、数百キロバイトの連結で命令列がINT_MAX(約2GiB)を超え、ジャンプの相対値が桁あふれします。その結果、照合のときに正規表現の仮想マシンの実行位置が命令列の外へ出て、攻撃者の影響が及ぶヒープ上の領域へ移ります。検知ルールの説明は、これがgitアカウントの権限でのコマンド実行につながるとしています。
未認証とされる理由と、公開された攻撃モジュールの前提
CVEレコードとGitLabの告知は「未認証の利用者」が攻撃できると書いています。一方、2026年10月30日にMetasploit Frameworkへ取り込まれた攻撃モジュールの説明は、攻撃の流れを2段階で示しています。まず、公開プロジェクトへpushできる利用者の認証情報を持つ攻撃者が、細工したCI設定とリポジトリのパスを置きます。次に、認証なしのCI Lint(CI設定の検証機能)への要求で、その正規表現をコンパイルさせ、GitLabのgitアカウントの権限でコマンドを実行します。
この説明を読む限り、コードの実行を引き起こす要求そのものは未認証ですが、事前の仕込みには公開プロジェクトへ書き込める利用者が要ります。誰でもアカウントを作れる設定(サインアップの開放)と公開プロジェクトを許しているGitLabは、その前提を攻撃者が自分で満たせます。モジュールの説明は、1回の試行で2GiBを少し超えるメモリを確保し、実行後にPumaのワーカー(Railsを動かすプロセス)が落ちるとも書いています。GitLabの検知ルールも、CVE-2026-97229の第2段として、同じ攻撃者が最後の要素に非ASCIIのバイトを含む255バイト近いパスのファイルをコミットする動きを挙げており、事前の書き込みが必要という読み方と合います。
公開されたモジュールは悪用の難しさを下げます。BleepingComputerは2026年11月2日に、Shadowserverが「CVE-2026-97229に脆弱なGitLabを1,000台以上追跡している」と述べたと報じました。同じ報道によれば、後述のCVE-2026-110264に脆弱なものは、毎日観測される約3万9,000台のうち1万1,300台以上です。
同じ系統の3件のCVEと修正版
GitLabは、Onigmoの不具合を突く脆弱性を、ほかに3件公開しています。Rubyの告知とCVEレコードを突き合わせると、次のとおりです。GitLabの検知ルールの資料は、19.4.1でのCVE-2026-93577の修正が不完全で、CVE-2026-97229はそれを回避したものだと記載しています。
| CVE | 不具合(Rubyの修正番号) | 認証 | CVSS v3.1 | GitLabの修正版 |
|---|---|---|---|---|
| CVE-2026-89078 | 解析に失敗したときの二重解放(#13332) | 必要 | 9.9 | 19.4.1、19.3.3、19.2.7 |
| CVE-2026-93577 | コンパイル後の大きさの整数オーバーフロー(#19020) | 必要 | 9.9 | 19.4.1、19.3.3、19.2.7 |
| CVE-2026-97229 | 93577と同じ不具合をCI/CDの経路から(#19020) | 不要 | 10.0 | 19.4.2、19.3.5、19.2.8 |
| CVE-2026-110264 | 繰り返しの多いパターンでの内部IDのオーバーフロー(#16801) | 不要 | 10.0 | 19.5.1、19.4.3、19.3.6、19.2.9、19.1.9、19.0.10、18.11.13 |
KEVに追加されたのはCVE-2026-97229だけです。CVE-2026-110264はKEVに載っておらず、CISAのSSVC評価は悪用がnone、自動化のしやすさがyesです(10月21日時点)。ただしCVE-2026-110264は7.0以上のほぼすべての版に影響し、未認証でCVSSも10.0です。19.2より古い系列はCVE-2026-97229の影響を受けませんが、CVE-2026-110264の影響は受けます。
更新先は、CVE-2026-110264の修正版を基準に選ぶと、4件すべてを一度に閉じられます。19.4.3以降、19.3.6以降、19.2.9以降は、それぞれCVE-2026-97229の修正版より新しいためです。
| 使っている系列 | 更新先(4件すべてを含む版) |
|---|---|
| 19.5 | 19.5.1以降 |
| 19.4 | 19.4.3以降 |
| 19.3 | 19.3.6以降 |
| 19.2 | 19.2.9以降 |
| 19.1 | 19.1.9以降(97229の影響なし、110264は影響あり) |
| 19.0 | 19.0.10以降(同上) |
| 18.11以前 | 18.11.13以降。18.10以前は修正版が出ていないため、サポート中の系列へ上げる |
注意
GitLabの公式パッケージ(Linuxパッケージ)とコンテナイメージには、Rubyの修正が当てられた状態で同梱されています。ソースからのインストールなど、GitLabが自前のRubyで動いている場合は、GitLabの更新に加えて、Rubyを3.3.13、3.4.12、4.0.9以降へ上げる必要があるとGitLabは19.5.1の告知で書いています。公式パッケージ同梱のRubyは修正を当てた状態のため、版の表示だけでは修正の有無を判断できません。GitLab自体の版で判断します。
GitLabの告知は、いずれの脆弱性にも回避策を示しておらず、更新だけを対策としています。19.4.2のパッチにはデータベースの移行が含まれ、単一ノードの構成では移行が終わるまでGitLabが起動しないため、停止時間を見込みます。複数ノードの構成では無停止の更新手順を使えます。
更新までのあいだに露出を減らす設定
公式の回避策がないため、ここに挙げるのは修正の代わりではなく、更新の準備が整うまでの間に攻撃の前提を減らすための運用上の設定です。公開された攻撃モジュールの前提(公開プロジェクトへ書き込める利用者と、未認証のCI Lintへの要求)から逆算しています。
- GitLabへの接続元を、VPNや社内網、許可したIPアドレスに限る
- 管理画面のサインアップの設定で、誰でもアカウントを作れる状態を止める(承認制やドメインの制限にする)
- 公開(Public)のプロジェクトとグループを棚卸しし、不要な公開をやめる
- 管理者以外が使っていないアカウントや、最近作られた見覚えのないアカウントを確認する
接続元を限っても、内部の利用者やすでに作られたアカウントからの攻撃は止まりません。設定を入れた後も、更新は急ぎます。
侵害の有無を点検する手順
KEVの項目は侵害の有無を調べることを求めています。GitLabは19.4.2の告知で、セルフマネージド版の検知として6つの名前を挙げています。Onigmoのネイティブなワーカーのクラッシュ、GraphQLのciLintへの悪意ある正規表現、CIの正規表現の大きすぎる非ASCIIのパス、CIの正規表現のガードによる拒否、CI LintでのWorkhorseのワーカーのクラッシュ、スクリプト系のクライアントによるCI Lintへの要求での5xxエラーの集中です。これらを手がかりに、更新の前後で次の順に点検します。
- 1
版と公開範囲を確かめる
管理画面のヘルプか、Linuxパッケージなら
sudo gitlab-rake gitlab:env:infoでGitLabの版を確かめます。影響する版で、インターネットから到達でき、サインアップと公開プロジェクトを許していた期間があったかを書き出します。 - 2
ワーカーの異常終了を探す
Pumaのログ(Linuxパッケージでは/var/log/gitlab/puma/)で、ワーカーの予期しない終了や再起動、メモリの急増が繰り返されていないかを確かめます。公開された攻撃モジュールは、1回の試行ごとにワーカーを落とすと説明されています。
- 3
CI Lintへの要求を洗い出す
Railsのログ(Linuxパッケージでは/var/log/gitlab/gitlab-rails/)を見ます。GraphQLのciLintへの要求はgraphql_json.logのvariablesに正規表現がそのまま残り、ガードが拒否したパターンはapplication_json.logに記録されます。REST APIのci/lintへの要求はapi_json.logでCI設定の中身が伏せられるため、接続元、クライアントの種類、5xxエラーの繰り返しで判断します。
- 4
記録に残らない要求を突き合わせる
ワーカーを落とした要求そのものはRailsのログに残りません。Workhorseのログを集めている場合は、ci/lintや/api/graphqlへの502のうち、相関ID(correlation_id)がRailsのログに見当たらないものを探します。ログに該当する要求がないことは、侵害がなかった証拠になりません。あわせて、最近のコミットに非ASCIIのバイトを含む極端に長いパスのファイルがないかを確かめます。
- 5
サーバー上の痕跡を確かめる
gitアカウントの権限で動いている見覚えのないプロセス、GitLabのサーバーから外部への不審な通信、gitアカウントのホームや一時ディレクトリに置かれた不審なファイルを確かめます。
- 6
侵害が疑われたら秘密情報を入れ替える
コードの実行まで進んだ形跡があれば、サーバーの再構築を前提にします。GitLabのサーバーには、CI/CDの変数、Runnerの登録トークン、利用者のアクセストークン、gitlab-secrets.jsonの鍵などが集まっているため、それらを入れ替えます。
GitLabのサーバーが侵害されたときに入れ替える秘密情報とログの見方は、同じGitLabのKEV入りの脆弱性を扱った次の記事でも整理しています。
あわせて読みたい
GitLabのCVE-2026-85706がKEV入り。認証なしでサーバー上のファイルが読まれるcommits APIのパストラバーサルと更新手順
利用者の入力から正規表現を作るRubyアプリも対象
不具合の本体はRubyにあるため、GitLab以外のRubyアプリも影響を受けることがあります。Rubyの告知によれば、影響するのは攻撃者が操作できる文字列から正規表現をコンパイルするアプリだけです。Regexp.new、Regexp.union、Regexp.compileに入力を渡す書き方や、/#{input}/のように正規表現のリテラルへ入力を埋め込む書き方が該当します。開発者が書いた正規表現だけを使うアプリは影響を受けないとされています。
Rubyが示す対策は、4.0.9、3.4.12、3.3.13以降への更新です。更新できない場合は、信頼できない入力から正規表現をコンパイルしないようにします。Rubyは次の2点も明記しています。
Regexp.timeout(照合時間の上限)では防げない。不具合は照合の前のコンパイルで起きるため- パターンの長さの制限も確実な防御にならない。短いパターンで起きる不具合もあるため
検索機能や絞り込み条件で利用者に正規表現を書かせているRubyアプリは、まずソースコードから該当する書き方を探します。
# 入力から正規表現を組み立てている可能性がある箇所を探す
grep -rnE 'Regexp\.(new|union|compile)|/#\{' app lib
見つかった箇所は、本当に利用者の入力が届くかを確かめます。届く場合は、Rubyを更新したうえで、利用者に正規表現そのものを書かせない設計(部分一致の検索に置き換えるなど)を検討します。正規表現のコンパイルとは別に、照合の時間が爆発するReDoSの対策は次の記事で解説しています。
あわせて読みたい
ReDoS(正規表現によるサービス拒否)の仕組みと対策。短い入力でCPUを食い潰すバックトラックを塞ぐ
対応チェックリスト
- セルフマネージド版のGitLabの版を確かめ、19.5.1、19.4.3、19.3.6、19.2.9、19.1.9、19.0.10、18.11.13以降のいずれかへ更新したか
- 18.10以前の系列を使っている場合、修正が出ているサポート中の系列へ上げる計画を立てたか
- ソースからのインストールなど自前のRubyで動かしている場合、Rubyを3.3.13、3.4.12、4.0.9以降へ上げたか
- 更新までの間、接続元の制限、サインアップの停止、公開プロジェクトの見直しを入れたか
- Pumaのワーカーの異常終了とCI Lintへの要求をログで確かめたか
- 侵害の形跡がある場合、サーバーの再構築とCI/CDの変数、Runnerのトークン、アクセストークンの入れ替えを行ったか
- 社内のRubyアプリで、利用者の入力から正規表現を組み立てている箇所を洗い出したか
CI/CDの基盤を本番と同じ重みで守る
GitLabのようなCI/CDの基盤には、ソースコード、ビルドの手順、デプロイ先の認証情報が集まります。今回の脆弱性は、パイプラインの設定という「開発者が書くもの」を入口に、基盤のサーバーそのものを奪える点で、基盤の守りを本番環境と同じ重みで扱う必要を示しています。修正版への更新を最優先にし、そのうえで接続元とアカウントの管理を見直します。パイプラインに渡す秘密情報やRunnerの分離など、CI/CD全体の守り方は次の記事にまとめています。
あわせて読みたい
CI/CDパイプラインのセキュリティ対策、GitHub ActionsとGitLab CIで秘密情報とRunnerを守る設計
出典・参考
- GitLab: GitLab Patch Release: 19.4.2, 19.3.5, 19.2.8(2026-10-12)
- GitLab: GitLab Patch Release: 19.4.1(CVE-2026-89078、CVE-2026-93577)
- GitLab: GitLab Patch Release: 19.5.1(CVE-2026-110264、2026-10-21)
- Ruby: Regexp fixes for GitLab CVEs(2026-10-23)
- GitLab Security: 検知ルールgraphql_cilint_hostile_regexp(技術説明とログ)
- ruby/ruby: Avoid overflow in the regexp compiler's program size arithmetic(PR #19020)
- CVE Record: CVE-2026-97229
- NVD - CVE-2026-97229
- CVE Record: CVE-2026-110264
- CISA: Known Exploited Vulnerabilities Catalog
- rapid7/metasploit-framework: Add Exploit Module for GitLab RCE via CI Lint [CVE-2026-97229](PR #22017)
- BleepingComputer: Over 1,000 GitLab servers vulnerable to ongoing RCE attacks(2026-11-02)
- CWE-190: Integer Overflow or Wraparound
関連する記事
CI/CDパイプラインのセキュリティ対策、GitHub ActionsとGitLab CIで秘密情報とRunnerを守る設計
CI/CDのパイプラインには、ソースコードへの書き込み権限、クラウドの認証情報、本番へのデプロイ権限が集まります。OWASPのCI/CDの10大リスクを土台に、パイプライン定義の変更管理、外部からのプルリクエストの扱い、トークンの最小権限、OIDC、依存の固定、Runnerの分離を、GitHub ActionsとGitLab CIの公式文書で整理します。
GitLabのCVE-2026-85706がKEV入り。認証なしでサーバー上のファイルが読まれるcommits APIのパストラバーサルと更新手順
2026年9月11日にCISAのKEVカタログへ追加されたGitLab CE/EEのCVE-2026-85706を、GitLab公式のCritical Patch Releaseで整理します。影響版18.7以降の読み方、19.3.2、19.2.6、19.1.8への更新、同時修正のCVE-2026-87719、更新後の秘密情報の入れ替えとログ確認まで解説します。
ReDoS(正規表現によるサービス拒否)の仕組みと対策。短い入力でCPUを食い潰すバックトラックを塞ぐ
ReDoS(CWE-1333)を、バックトラック型エンジンが失敗時に経路を総当たりして指数時間や多項式時間に陥る機構から整理します。危険なパターンの見分け方、CloudflareとStack Overflowの障害例、Go/RE2/Rust/.NET/Java/Python/Ruby/Node.jsごとの対策、静的検出ツール、入力長の上限やタイムアウトなど設計面の守りとコードレビューの観点まで解説します。


