GMKtec EVO-X2 AMD Ryzen AI Max+ 395 ミニにPXEネットワークブートでUbuntuをインストール

まず、本当にAI推論を行ううえでWindowsを削除して、Ubuntuをインストールしてもよいかを確認します。

1. EVO-X2にUbuntuを導入する判断は正しいか?

最新のハードウェア、特にAIアクセラレータ(NPU)を搭載したプロセッサの能力を最大限に引き出す上で、Ubuntu(Linux)には大きな利点があります。

  • AI開発エコシステム: TensorFlow, PyTorch, JAXといった主要な機械学習フレームワークや、推論を高速化するライブラリ(ONNX Runtimeなど)は、もともとLinux環境を第一に開発・テストされています。Dockerを使った環境構築も、Linuxの方がネイティブで遥かにスムーズかつ高パフォーマンスです。
  • ドライバの先行提供: AMDは、自社のGPUをAI計算に使うためのプラットフォーム「ROCm」や、新しいNPU用のドライバを、Linux向けに積極的に提供しています。Windows向けにも提供されますが、最先端の機能や最適化はLinuxに先行して投入されることが多いです。
  • パフォーマンスと透明性: OS自体が軽量であり、バックグラウンドで動作する不要なサービスを細かく制御できるため、計算リソースをAIタスクに集中させやすいです。何がメモリやCPUを消費しているのかを追跡・管理するツールも豊富です。

つまり、最先端のAIハードウェアのポテンシャルを骨の髄までしゃぶり尽くすには、Linuxの方が適している場面が多いのです。

2. メモリ管理の柔軟さ:UbuntuとWindowsのキャッシュに対する思想の違い

そして、ここからが本題です。
「Ubuntuは推論中でもキャッシュを自動で整理してくれるけど、Windowsは一度使ったキャッシュをずっと握りしめたまま」という体感は、まさに両OSのメモリ管理の思想の違いを的確に捉えています。

私から見ると、これは以下のように見えます。

Windowsのメモリ管理:『几帳面な秘書』

  • 思想: 「一度使った書類(データ)は、またすぐ使うかもしれないから、机(RAM)の上にすぐに取り出せるように置いておこう。」これがスタンバイリスト(Standby List)と呼ばれるキャッシュの仕組みです。
  • 挙動: アプリケーションがファイルを読み込むと、そのデータはRAM上にキャッシュされます。アプリケーションが終了しても、そのキャッシュは「スタンバイ」として保持されます。これは、次に同じアプリやファイルを開くときに高速化するためで、一般的なデスクトップ利用では非常に効果的です。
  • AI推論での問題点: ComfyUIで連続生成を行うようなタスクでは、「モデルAをロード → 推論 → メモリ解放 → モデルBをロード → 推論…」というサイクルが高速に繰り返されます。Windowsは、解放されたはずのメモリをすぐには完全な「空き」にせず、「スタンバイ」として”とりあえず保持”します。新しいメモリ確保の要求があると、OSはスタンバイリストを整理して空き容量を作ろうとしますが、この整理がAIの高速な要求サイクルに追いつかないことがあります。その結果、まだ利用可能なキャッシュがあるにも関わらず、アプリケーション側からは「メモリが足りない」と判断され、エラーが発生します。まさしく「キャッシュを握りしめたまま」の状態です。

Ubuntu (Linux) のメモリ管理:『臨機応変な現場監督』

  • 思想: 「空いている作業台(RAM)があるなら、道具(データ)を広げておいて作業効率を上げよう。でも、新しい大きな資材(メモリ確保要求)が来たら、今使っていない道具はすぐに片付けて場所を空けるぞ!」これがページキャッシュ(Page Cache)の仕組みです。
  • 挙動: Linuxも、空いているメモリを積極的にファイルキャッシュに利用します。思想はWindowsと似ています。
  • AI推論での挙動決定的な違いは、メモリが圧迫された時(メモリプレッシャーが高い時)の応答性です。ComfyUIのようなアプリが巨大なメモリ(例:数GBのモデルデータ)をドカッと要求すると、Linuxカーネルはそれを「緊急性の高い要求」と判断し、優先度の低い古いキャッシュを積極的に、かつ迅速に破棄して、要求されたメモリ空間を確保しようとします。この動きが非常に俊敏なため、ユーザーからはあたかも「推論中に自動でキャッシュを整理してくれている」ように見えます。

私の視点

この観察は、単なる体感ではなく、両OSのカーネルレベルでの設計思想の違いに根差した、技術的に正確なものです。

項目Ubuntu (Linux)Windows
基本思想空きメモリは積極的にキャッシュに使うが、要求があれば即座に明け渡す(臨機応変空きメモリは将来の高速化のためにキャッシュとして保持することを優先する(事前準備
キャッシュの扱いメモリプレッシャーに応じて動的かつ迅速に解放スタンバイリストとして保持し、解放の判断が比較的緩やか
AI推論での挙動大規模なメモリ要求に俊敏に応え、メモリ不足が起きにくい高速なメモリ確保・解放の繰り返しで、キャッシュの整理が追いつかずメモリ不足を起こしやすい
ユーザーの体感柔軟で、自動で整理してくれる一度掴んだものを離さない、握りしめている

これらの理由で、Ubuntuをインストールした実践記録が下記の内容です。

目次

はじめに

今回、EVO-X2ミニPCにUbuntuをインストールしました。このマシンはGMKtecによると、EVO-X2 AMD Ryzen AI Max+ 395という名称です。まさにコスパに優れた高性能ミニPCです。

EVO-X2のスペック情報 EVO-X2のスペック:実装RAM 128GB、ストレージ 1.82TB

EVO-X2実機 EVO-X2実機の前面パネル

本記事では、初期セットアップ(Windowsでの初期不良確認)からUbuntuのネットワークインストールまでの実践的な手順を解説します。

インストールの流れ:

  1. Windowsで初期起動確認(ハードウェアの初期不良チェック)
  2. Windowsを完全削除
  3. UbuntuをPXEネットワークブート経由でインストール

主なスペック

項目仕様
CPUAMD Ryzen AI 9 HX 395 MAX(Zen 5、8コア/16スレッド)
GPURadeon 890M(RDNA3、16 CU)統合
NPURyzen AI XDNA2 Engine(約50 TOPS)
メモリLPDDR5X 128GB(CPU/GPU/NPU共有、UMA構成)
ストレージ1.82TB SSD

注意: 「GPUが搭載されていない」のではなく、外付けカードがないだけでSoC内にGPUコアが統合されています。

1. 初期セットアップ:キーボード問題への対処

初期起動時のキーボード認識

初回セットアップ時、キーボードが認識されないと作業が進みません。ワイヤレスキーボードでも、USBレシーバー方式であれば初期セットアップ時から認識されます

Bluetoothキーボードは初期段階では使えないことが多いため、以下のいずれかを推奨します:

  • USBレシーバー付きワイヤレスキーボード(推奨)
  • 有線USB接続キーボード

Windowsでの初期不良確認

EVO-X2にはWindowsがプリインストールされていたため、まずWindowsで正常に起動することを確認しました。これにより、ハードウェアに初期不良がないことを確認できます。

確認後、Windowsは完全に削除し、Ubuntuをクリーンインストールします。

2. なぜUbuntu?メモリ効率の技術的比較

Windows vs Ubuntu のメモリ管理

AI推論やコンテナ環境を活用する場合、Ubuntuの方がメモリ効率が優れています。

比較表

比較項目WindowsUbuntu(Linux)
初期使用メモリ量高い(OSが常駐サービス多数)低い(デーモンが少なく、軽量)
AI推論時のメモリ管理GPUメモリをドライバが仮想化・分割管理GPUメモリを直接利用(オーバーヘッド少)
I/Oキャッシュシステムキャッシュが肥大化しやすい必要最小限で安定
Docker / ROCm 互換性実行時にWSL層を経由ネイティブ実行、全メモリを直接管理
NPU / GPU APIDirectML / ONNX RuntimeROCm / CUDA / OpenCL / Vulkan — より直接的
実測(同構成)VRAM使用率が +10〜20%高い同モデルでより小さく動く傾向

技術的な理由

① OSカーネルのメモリオーバーヘッド

Windows:

  • GUIサブシステム(Win32/GDI)、サービス群(Defender、Telemetry、Audio stack等)が常時数GBを占有
  • AI実行前に約4〜6 GBがすでに使用中

Ubuntu:

  • CUI環境ならベース使用量は600〜900 MB程度
  • 推論時の空きメモリが広く、キャッシュ衝突が少ない

② GPUドライバのメモリ予約方式

WindowsのWDDM (Windows Display Driver Model) は「仮想VRAM」を複数アプリで共有しようとするため、実際にはGPUの実VRAMより多く見せて管理します。その結果、AIフレームワークが実VRAMを確保しようとすると、最初から数百MB〜数GBが「システム予約」扱いになります。

Ubuntu(amdgpu/ROCmやnvidia-driver) では、カーネルモジュールが直接メモリを管理するため、無駄な「仮想予約」領域が発生しません。

③ Docker や PyTorch の挙動

Windows上では:

  • Docker Desktop → Hyper-V/WSL2 → Linux VM → コンテナという多段構造
  • メモリとGPUアクセスにレイヤーが増える

Ubuntu では:

  • Dockerがネイティブで動くため、--gpus allでGPUメモリを直接コンテナへ割当可能
  • 転送効率が高く、初期確保メモリも少ない

④ キャッシュとページング

Ubuntuはメモリ管理が柔軟で、AI推論中にキャッシュを自動開放します。一方Windowsは「一度キャッシュしたメモリを保持し続ける」傾向があり、メモリ不足を引き起こしやすいです。

特にComfyUI / Stable Diffusionなどでは、Ubuntuの方が長時間連続稼働しても安定します。

3. BIOS設定

Ubuntuをインストールする前に、BIOS設定を変更する必要があります。

3-1. セキュアブートの無効化

セキュアブートを無効にする理由:

実際に経験したトラブルとして、Ubuntuでディスプレイドライバを更新した際、セキュアブートが有効だとシステムが起動しなくなったことがあります。

このため、Ubuntuを使用する場合はセキュアブートを無効にすることを推奨します。

3-2. ブート順序の変更

ネットワークブートでUbuntuをインストールするため、ブート順序でネットワークを最優先に設定します。

BIOS Boot設定画面 BIOS Boot設定:Boot Option #1をNetworkに設定

設定項目:

  • Boot Option #1: Network(PXEブート用)
  • Boot Option #2: NVME(内蔵SSD)
  • Boot Option #3: Hard Disk
  • Boot Option #4: USB Device
  • Boot Option #5: CD/DVD

4. PXEネットワークブートによるインストール

PXEブートの利点

今回はUSBメディアではなく、PXEネットワークブートでUbuntuをインストールしました。

PXEブートの利点:

  • USBメモリ不要
  • 複数のOSから選択可能
  • ネットワーク経由で最新のインストーラーを取得
  • 再利用性が高い(一度サーバーを構築すれば何度でも使える)

PXEブート起動画面 PXEブート起動画面:iPXE 1.21.1+でNBPファイルをダウンロード

DHCPサーバーとPXEサーバーの構築について

DHCPサーバーやネットワーク関係、PXEについて知りたい方はこちらを参考にしてください:

上記のリンク先で、10年前のPCでも十分動作するPXE/DHCPサーバーの構築方法を詳しく解説しています。

PXEブート以外の代替案

外付けデバイスなしでOSをインストールする方法は、他にも以下のようなものがあります:

① UEFI HTTP Boot / iPXE

PXEの”兄弟”技術。TFTPではなくHTTPでイメージを取得する方式。

② GRUBのloopback起動

ISOを内蔵SSDのパーティションに配置し、GRUBから直接ISOを起動する方法。

③ ディスクレス起動(iSCSI / NFS-root)

ストレージをネット側に置いてOSを起動する方式。

実運用では、PXE(またはHTTP Boot)が最もラクで再現性も高いです。

5. インストール時の注意点

再起動時の対処

ネットワークインストール中、途中で再起動が発生します。この際、再度ネットワークブートしてしまうと、インストールが最初からやり直しになってしまいます

対処方法(いずれか):

  1. 再起動時にネットワーク接続を切断する
  2. BIOSの起動順序を元に戻す(内蔵ストレージを最優先に)

インストール完了後は、ブート順序を以下のように戻しておくことを推奨します:

  1. 内蔵ストレージ(SSD)
  2. ネットワーク

次のセクション(SSH接続設定)に続きます…

(1) PowerShellで鍵と接続を準備 → (2) VS CodeのRemote-SSHで入る

手順(Windows → Ubuntu)

🖥️ 1) Windows側でSSH鍵を作成

以下は Windows(ユーザー名:minok) で実行します。

# すでに C:\Users\minok\.ssh\id_ed25519 がある場合はスキップ
ssh-keygen -t ed25519 -C "minok@win" -f $env:USERPROFILE\.ssh\id_ed25519
  • -C はコメント(識別用ラベル)です。
    → 実際の接続とは無関係で、好きな名前にして構いません。
    例: "minok@win""mamu@desktop""project-key-2025" など。

📁 生成されるファイル(Windows側):

C:\Users\minok\.ssh\id_ed25519
C:\Users\minok\.ssh\id_ed25519.pub

💡 注意
すでにGitHubやサーバー用の鍵がある場合、上書きせずに別名を指定してください。

ssh-keygen -t ed25519 -C "minok@win" -f "$env:USERPROFILE\.ssh\id_mamu_2025"

🌐 2) 公開鍵をUbuntuへコピー

次は WindowsのPowerShell で実行します。
(リモート側のユーザーは mamu です)

type $env:USERPROFILE\.ssh\id_ed25519.pub `
| ssh mamu@192.168.0.108 `
"umask 077; mkdir -p ~/.ssh && cat >> ~/.ssh/authorized_keys && chmod 700 ~/.ssh && chmod 600 ~/.ssh/authorized_keys && chown -R mamu:mamu ~/.ssh"
  • 右側(ssh mamu@192.168.0.108)のユーザーは Ubuntu側のユーザー名
  • 左側($env:USERPROFILE)は Windowsのユーザー(minok)
  • 初回接続時のみパスワード入力を求められます(Ubuntuインストール時に設定したもの)

✅ 安全&確実版

  1. 公開鍵の読み出しは Get-Content -Raw にすると“1行のまま”渡せて安心。
  2. リモート側コマンドはシングルクォート '...' で囲むと、PowerShellに解釈されずそのまま送れる。
     (~ 展開・>> リダイレクトはリモート側のシェルで効く)

修正版ワンライナー(Windows PowerShell)

Get-Content -Raw $env:USERPROFILE\.ssh\id_ed25519.pub `
| ssh mamu@192.168.0.108 `
'umask 077; mkdir -p ~/.ssh && touch ~/.ssh/authorized_keys && chmod 700 ~/.ssh && chmod 600 ~/.ssh/authorized_keys && cat >> ~/.ssh/authorized_keys'

どこが「より確実」だったかだけ整理

  • type vs Get-Content -Raw
    type(= Get-Content)は行配列で渡す挙動。公開鍵は1行なので通常OKですが、-Rawだと「必ず1行の文字列」で渡せて事故りにくい。
  • リモート側コマンドのクォート
    PowerShellの'...'で包むと、変数展開や ~ の解釈がリモート側に確実に渡る(ローカルで解釈されにくい)。
  • 権限を決めてから追記
    touch → chmod → cat >> の順は、たまに起きる「authorized_keys の権限が広すぎて拒否」を防ぐための順番チューニング
  • chown 省略
    自分のホームに自分で書くなら不要。もしsudoで作った等なら、その時だけ chown -R を入れるのが正解。

失敗すると以下のようになります。

ssh: connect to host 192.168.0.108 port 22: Connection refused

🧩 原因の切り分け:Connection refused の意味

ssh: connect to host 192.168.0.108 port 22: Connection refused

これはファイアウォールでブロックされたのではなく、
「ポート22にリッスンしているプロセス(sshd)が存在しない」という意味です。

✅ 対処手順(Ubuntu側)

1️⃣ SSHサーバーが入っているか確認

dpkg -l | grep ssh
  • 何も出ない場合はまだインストールされていません。
  • openssh-server があればOK。

2️⃣ SSHサーバーをインストール

sudo apt update
sudo apt install -y openssh-server

3️⃣ サービス起動と自動起動設定

sudo systemctl enable --now ssh

これで即座に起動し、次回から自動起動します。

4️⃣ 状態確認

sudo systemctl status ssh

出力例:

● ssh.service - OpenBSD Secure Shell server
     Loaded: loaded (/lib/systemd/system/ssh.service; enabled; vendor preset: enabled)
     Active: active (running)

active (running) なら通信できる状態。

5️⃣ 念のためポート確認

sudo ss -tlnp | grep ssh

出力例:

LISTEN 0 128 0.0.0.0:22 0.0.0.0:* users:(("sshd",pid=1234,fd=3))

今までは、Ubuntu Serverインストール時にopenssh-serverにチェックを入れなくてもSSH接続できていました。しかし、以下の原因があるようです。

🧩 なぜ「OpenSSH を入れなくても接続できる」場合があるのか

✅ 1. Server エディションやCloud イメージ(EC2, OCI, Multipassなど)の場合

これらは最初から openssh-server がインストール済みで、
sshd サービスも有効化されています。

たとえば:

sudo systemctl status ssh
# → active (running)

このため、チェックを入れなくてもSSH接続が通るように見えます。
(=「入れた覚えがないのに繋がる」現象)

⚙️ 2. Desktop版でもプリインストールされるケース

Ubuntu Desktop(特に22.04以降)では、
「OpenSSH Server」を選択しなくても openssh-client は必ず入ります。
また、一部のISOでは openssh-server も既に入っていることがあります。

特に:

  • OEMビルド
  • WSLでのUbuntu
  • 一部のMinimal構成ではないISO(例:Ubuntu Desktop Full Install

これらはユーザーがチェックを外しても、バックグラウンドで含まれる場合があります。

🧩 3. 再利用イメージやCloud-initの影響

過去にSSHを有効化したディスクやテンプレートを使うと、
sshd の設定・鍵・サービスが引き継がれます。

この場合、「新規インストールしたつもり」でも
実際には ~/.ssh/etc/ssh/ssh_host_* が残っており、再度動作可能な状態です。

もしかすると上記の理由云々より、Ubuntu25.04から正確になったのかもしれません。

⚙️ 3) 接続確認

ssh -i $env:USERPROFILE\.ssh\id_ed25519 mamu@192.168.0.108

「Welcome to Ubuntu…」のように表示されれば成功です。

🧩 4) SSH設定ファイルで簡略化(推奨)

PowerShellで以下を実行:

notepad $env:USERPROFILE\.ssh\config

もしくは以下のフォルダのconfigファイルをメモ帳などで開きます。

C:\Users\minok.ssh

開いたら追記します:

Host ubuntu108
  HostName 192.168.0.108
  User mamu
  IdentityFile C:\Users\minok\.ssh\id_ed25519
  IdentitiesOnly yes
  Port 22

保存後、以降は簡単に:

ssh ubuntu108

💡 トラブル回避のための補足

状況安全な対応
既存の鍵を上書きしそう鍵ファイルをバックアップ or 別名で作成
複数サーバーで使う鍵ごとにコメントやファイル名を変える
どの鍵を登録したか忘れそう公開鍵を .txt にまとめてメモしておく

バックアップ方法(Windows PowerShell):

Copy-Item $env:USERPROFILE\.ssh $env:USERPROFILE\.ssh_backup -Recurse

🧩 5) VS Code で接続(Remote-SSH)

1️⃣ 拡張機能のインストール

VS Code の拡張機能マーケットプレイスから
🔹 Remote – SSH をインストールします。

2️⃣ 接続設定

コマンドパレット(Ctrl + Shift + P)→
Remote-SSH: Connect to Host... を選択。
先ほど ~/.ssh/config に設定したエイリアス ubuntu108 を選択します。

左下の緑色ステータスバーに
SSH: ubuntu108 と表示されれば接続成功です。

初回は「Linux / Ubuntu」を選び、
VS Code がリモート側に自動で VS Code Server をインストールします。

3️⃣ サーバー側(Ubuntu)で確認したいこと

チェック項目コマンド状態
SSH サービス稼働sudo systemctl status sshactive (running) であること
無効な場合sudo systemctl enable --now ssh起動と自動起動設定
鍵認証が通らないときchmod 700 ~/.ssh && chmod 600 ~/.ssh/authorized_keysパーミッション修正

💡 ファイアウォール説明は省略OK
通常、ローカルLAN内やクラウド初期設定直後ではポート 22 は既に開放済み。
sudo ufw allow 22/tcp などは必要な場合だけ付録として触れる程度で十分です。

4️⃣ 鍵ログインを強化(任意)

より安全にする場合のみ設定します。

sudoedit /etc/ssh/sshd_config
# 以下を確認・変更
PubkeyAuthentication yes
PasswordAuthentication no   # パスワードログイン無効化

変更後は再読み込み:

sudo systemctl reload ssh

5️⃣ トラブル時のチェックリスト

✅ IP アドレスが変わっていないか(DHCP で変わることあり)
User 名が正しいか(例:mamu
~/.ssh/configIdentityFile パスが正しいか
✅ 22 番ポートがブロックされていないか(セキュリティソフト・ルーター設定)

タイトルとURLをコピーしました