APUでDirectML

APUと言うのはCPUパッケージ内にGPUを搭載したものをAMDがそう呼称してから始まった。2011年である。

Intel互換CPUを扱っていたAMDRadeonなどのGPUを扱うATI社を買収したことから生まれた。同タイミングでIntel社もそれまでチップセット側に搭載していた簡便なGPU機能をCPUパッケージ側に移動した。所謂iGPUである。そして現在まで続く。

 

個人的には2012年の日本AMD本社でのブロガー勉強会が印象に残っている。私も古くからPVの少ないブロガーではあるのでエントリーさせて頂いた。土産にAPUと聞いていたがマザーボードも付いてきた。(対応マザーがまだ少ないので入手できないと意味が無いから付けたとのことでした)

bleu48.hatenablog.com

 

その昔に3DNowやらMMXやらを使ってMP3を扱うような遊びをしていたので、こいつも取り扱えるかと思いきやとてもハードルが高く結局ソフトウェア開発には繋がらなかった。

 

で、昨今のAPUであるが今はOpenCLやVulkanで叩きやすくなっている。

今回はさらにMS社が扱いやすくしてくれているDirectMLから使ってみることにする。

といってもPythonから呼ぶライブラリが変わるだけでなんてことはなかった。

 

1.Onnxruntime

onnxruntime-directml · PyPI

なんてことはなくPyPIからpipコマンドでインストールして動く。

CPU動作のonnxruntimeやonnxruntime-gpuとわずかにオプションの扱いが変わる程度である。

具体的にはonnxruntimeではその実行バックエンドのことをproviderと呼ぶがそれを指定する以下の部分である。

providers=['DmlExecutionProvider']

 

2.PyTorch

torch-directml · PyPI

こちらはβ版であるので少し慎重に扱う。自分でビルドすれば最新版が扱えるがβ版のバイナリは特定バージョンのみで供給されている。そのうちPyTorch本体に取り込まれる可能性もあるとのこと。

また、ソースレベルでインポートする宣言

import torch_directml

やデバイス指定など

    device = torch_directml.device(torch_directml.default_device())

は変更する必要があるが概ねそれくらいで大概のプログラムは動く。

 

で、重要なのが実行速度であるが、これは同じAPUで扱う限りCPU動作より1~3倍くらい速くなった。速くなるためにはCPU‐GPU間の連携がうまくいかないといけないが小さな計算を高頻度で切り替えるとオーバーヘッドが大きくなって旨味が無い。こういうったアクセラレータはそのハードウェアに合わせたある程度の規模で行うことが重要である。もちろん、本格的なGPUを使うと100倍とか速くなるので本件ちょっとしたものでしかない。

 

ところで、昨今生成系AIと呼ばれる大型の推論モデルを動かすには巨大なGPUメモリが必要とされている。APUはメインメモリ内にビデオ用のメモリを確保するため専用GPUより遅いが、設定如何では大きなビデオメモリを確保することが可能である。(そもそもメインメモリがビデオメモリより仕様上随分遅い。)確保量もマザーボード側の設定が可能かどうかに依存する。(起動後に動的に変更できないのか気にはなる)

gigazine.net

 

こういうのも動くという曲芸であって速度的には非常に遅いのであまり期待しない方がいい。上記のとおりAPUだと精々CPUの数倍しか出ない。

 

ということでAPUで少し遊んでみた。一応無いよりマシといったところである。

毎度の注意点であるが、CPUパッケージ内の簡易なビデオ出力機能であるのでここに100%の負荷をかけるのは恐らく設計外の利用方法になる。昨今オーバーヒートでクロックを下げる仕組みはあるがこの部分の対応が弱い印象があり、つまりフリーズする。過剰に期待せずちょっと使えば少し幸せになるかもしれないくらいの機能と思った方がいい。

ーーー

追記:

現在最強のAPUがデスクトップではRyzen7 5700Gである。2万5千円くらいでZen3の8コアだから普通のCPUとしてみてもコストパフォーマンスが高い。

ノートPC用のZen4のAPUが出つつあって7840HSとか7940HSとかである。この辺はまだ高額過ぎて触れていないが前世代より若干強そうである。7840Uは早く普通のPCに搭載して頂きたい。

デスクトップ用のZen4にも2コアだけGPUが搭載されていてAPU的に使えるがこれは無いよりマシ程度なもので更に期待してはいけない。8コアくらい積んだ上に廉価化するのを期待する。

ーーー

追記2:

某書籍で参考にされることが多いpython-dlshogi2ですが

GitHub - TadaoYamaoka/python-dlshogi2

こいつもonnxruntime-directmlで動きます。

onnx_player.pyのここだけ変更すれば終わりです。

DirectMLに関してはiGPUとdGPUの両方があれば選択的に使えるのでオプション有効にしてあります。(それとCPUも)

    # モデルのロード
    def load_model(self):
        if self.gpu_id >= 0:
            self.session = onnxruntime.InferenceSession(self.modelfile, providers=['DmlExecutionProvider'], provider_options=[{'device_id': self.gpu_id}])
        else:
            self.session = onnxruntime.InferenceSession(self.modelfile, providers=['CPUExecutionProvider'])