0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【DGX Spark】ローカルLLMが不安定になった原因を切り分ける — NVRM NV_ERR_NO_MEMORY とユニファイドメモリ

0
Last updated at Posted at 2026-10-11

DGX Spark(GB10)で動かしていたローカルLLMスタックが「コンテナ再起動ループ」「応答遅延」を起こしたときの、
原因究明の手順と切り分け方をまとめます。構築編の続編ですが、単体でも読める内容です。

※ IPアドレス・ホスト名・認証情報はプレースホルダに置き換えています。

シリーズ


1. 症状

前提: 2つの推論サーバを併用していました。tensorfold = Qwen3.8-27B(主に使う側)、tensorfold2 = Qwen3.6-35B-A3B です。

  • 推論コンテナの一方(Qwen3.6-35B-A3B 側)が数十秒周期で再起動を繰り返す。
  • 応答が遅い・タイムアウトする。特に長いコンテキストで顕著。
  • ホストのSSHは生きているので「ホスト全体の停止」ではない。

2. まず「どのコンテナが落ちているか」を特定する

# 稼働状況と再起動回数
docker ps -a --format 'table {{.Names}}\t{{.Status}}'
for c in tensorfold tensorfold2 tensorfold-litellm-1; do
  printf '%s: ' "$c"
  docker inspect -f '{{.State.Status}} restarts={{.RestartCount}} exit={{.State.ExitCode}} oom={{.State.OOMKilled}}' "$c"
done

実際には Qwen3.6-35B-A3B 側のコンテナが restarts=96 まで増えており、exit=1(アプリ異常終了)でした。

ライフサイクルイベントで「再起動の周期」も見えます。

docker events --since 1h --until 0s --filter type=container \
  --format '{{.Time}} {{.Actor.Attributes.name}} {{.Action}} exit={{.Actor.Attributes.exitCode}}' \
  | grep -vE 'exec_'

Docker の restart: unless-stopped は指数バックオフで再起動するため、約60秒周期で start→die を繰り返す挙動になります。


3. アプリのログとカーネルログを見る

3.1 アプリ側

docker logs --tail 80 tensorfold2

3.2 カーネル側(決定的な証拠)

sudo dmesg -T | grep -iE 'nvrm|no_memory|oom|killed|reset' | tail -40
# もしくは
sudo journalctl -k --since '7 days ago' | grep -iE 'nvrm|no_memory'

ここで GPUメモリの確保失敗 が出ていました。

NVRM: nvCheckOkFailedNoLog: Check failed: Out of memory [NV_ERR_NO_MEMORY]
  returned from _memdescAllocInternal(pMemDesc) @ mem_desc.c:1359

3.3 日別に集計して「時系列」で切り分ける

これが最も効きました。 発生を日別に数えると、原因の時期がはっきりします。

sudo journalctl --since '45 days ago' -o short-iso \
  | grep 'NV_ERR_NO_MEMORY' | cut -c1-10 | sort | uniq -c

結果(例):

日付 発生回数
10/05 7
10/06 129
10/07 75
10/08 17
10/09 177

カーネルは 10/09 に更新していたが、急増は 10/06 から。
→ 「カーネル更新が原因」ではなく、その前に始まったメモリ逼迫が原因、と切り分けられます。


4. メモリの実態を把握する

free -h
grep -E 'MemTotal|MemFree|MemAvailable|Cached|Committed' /proc/meminfo
nvidia-smi --query-compute-apps=pid,process_name,used_memory --format=csv

GB10 の注意点: nvidia-smi のメモリ表示は Not Supported になります(ユニファイドメモリのため)。
メモリは free -h を見るのが正解です。

逼迫時の例:

               total   used   free  buff/cache  available
Mem:           121Gi   86Gi   30Gi        6.0Gi       34Gi
  • free が 30GiB しかない。
  • さらに free の数字には**ディスクキャッシュ(解放可能)**が含まれるため、実質は available を見ます。

5. 原因

  • GB10 は CPU/GPU がメモリを共有(MemTotal ≈ 121GiB)。
  • 2つのLLMサーバが同時稼働し、各コンテナのCUDAメモリ上限の合計が 64 + 50 = 114GiB。
  • 加えて shm_size: 16gb ×2、OS・他プロセス分。
  • ピーク時にオーバーサブスクライブ → NV_ERR_NO_MEMORY → コンテナ exit 1 → 再起動ループ。
MemTotal 121GiB に対して:
  tensorfold(27B) 上限64 + tensorfold2(35B) 上限50 + shm 16+16 + OS …
  → ピーク時に破綻

6. 対策

6.1 Qwen3.6-35B-A3B を縮小(応急処置)

項目 変更前 変更後
--context 188657 131072
CUDA_MEMORY_LIMIT_GB 50 44
shm_size 16gb 8gb

起動見積りが 42.3GiB → 32.1GiB に低下。

6.2 Qwen3.6-35B-A3B を停止(根本)

「1種類しか動かさない」方針に合わせ、compose 定義を無効化して停止。

docker compose stop tensorfold2   # tensorfold2 = Qwen3.6-35B-A3B
# compose ファイル上のサービス定義をコメントアウトし、depends_on からも外す
docker compose up -d

6.3 結果

時点 free
変更前 30 GiB
Qwen3.6-35B-A3B 停止後 80〜90 GiB

NV_ERR_NO_MEMORY は変更後 0件、コンテナは restarts=0 で安定。


7. 切り分けチェックリスト(再発時に)

  1. docker inspect で どのコンテナが落ちているか / RestartCount / ExitCode を確認
  2. docker logs でアプリ側のエラー
  3. dmesg/journalctl で NVRM / NO_MEMORY / OOM
  4. journalctl の 日別集計で「いつからか」を時系列で確認(=カーネル更新等との切り分け)
  5. free -h(available を見る)、nvidia-smi(GB10はN/A)
  6. コンテナの CUDAメモリ上限の合計 vs 実メモリ を電卓で確認
  7. shm_size の合計も忘れずに

8. 教訓

  • ユニファイドメモリでは「上限の合計」が命取り。天井が高くても、同時に伸びれば破綻する。
  • 不安定の切り分けは 「カーネル/ドライバ」より先に「メモリ」を疑う。日別集計が効く。
  • nvidia-smi が使えない GB10 では、free -h とコンテナ上限が一次情報。
  • 併存は便利だが、余白20GiB以上を残すか、片方を止める設計にする。

シリーズ

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?