Ryuz's tech blog

FPGAなどの技術ブログ

システムアーキテクチャ設計とは何なのか

はじめに

業種や分野を問わず「全体を見てシステムアーキテクチャ設計できる人が少ない」というような話はよく聞きます。

私も決してそういう設計の上級者でも何でもないのですが、長いエンジニア人生の中で、平均的な人よりはちょっとだけ多くそういう設計をする機会には恵まれてきたように思いますし、何よりお仕事とは関係なく趣味でオレオレアーキテクチャは沢山作ってきましたので、一体全体システム設計だとかアーキテクチャ設計だのを学ぶのの何が難しいのかというのを勝手気ままに考察してみたいと思います。

世の中には、シンプルで美しいアーキテクチャもあれば、複雑怪奇な継ぎはぎだらけで二度と触りたくないシステムまで様々です。後者をに関しては、設計した人を「システムアーキテクチャ設計できる人」と呼んではまずいケースも多々あるので、まあそういうのも含めて考察してみようと思います。

システムアーキテクチャ設計できる人が少ない理由

能力的な問題

まず人それぞれ得意不得意は必ずあります。私がいくら勉強しても英語が話せないとか、人の顔と名前覚えられないとか、絵心がさっぱりでダサいプレゼンしか作れないとか、まさにそれだと思ってます。個人的には、向かないことをわざわざ労力掛けても仕方ないので適材適所で分担すればいい話だとは思っています。

で、私の経験上、世の中には 全体はよくわからないけど部品なら作れるよ と言う人がそれなりの数いらっしゃいます。

でそういう方々にうまいこと得意分野を割り当てていって、ゴールを目指すスキルに長けている人をプロジェクトマネージャーと呼ぶわけです。

が、ここにちょっとだけ罠があって、「部品は作れるよ」という方々の中には 100点満点近い部品を作れる人もいれば、指摘や指導を繰り返してやっと60点のギリギリ及第点の部品を作れる人まで様々です。 少なくともソフトウェア開発の現場でのソフトウェア部品の個人差による品質バラツキは顕著にあるかと思います。

人間が一度に把握できるスコープは人それぞれですので、どうしても部分しか見れない人はここで壁にぶつかりがちな気がします。

一方でシステム設計できるように育っていく人は、部品がどう使われるのか、その外側の要件も視野に入れているので、部品に求められる要件の意味や行間まで考えて100点近い部品を作ってくる人が多いように思います。

スキル習得機会の問題

もう一点は、折角能力があっても、スキルを伸ばす機会がなかなか手に入らない事です。開発に携わる人間で ゴールを決める 工程に携われる機会は決して多くはありません。多くの場合は、誰かの決めたゴールを達成するための部品 を任される機会しかないのが実情でしょう。

そして私の知る範囲で、よくある2つの課題があります。

  • 全体像を教えてもらえることなく、ただ部品を作ることだけを指示されるケース
  • そもそもスキル習得にならない悪い見本のようなシステムの部品開発を指示されるケース

でしょうか。

特に前者は聞けば教えてもらえることもありますが、 NDA だったり組織の縦割り行政だったり、政治的理由で情報を教えてもらえないケースもあり、何に使うのかわからないまま部品を作らされるというケースがあります。

また後者も、これをそのまま受け入れてしまう人も多いのですが、それだとそれ以上成長できなくなってしまいますので、まだ、システムのダメさ加減を愚痴りながら仕事してるエンジニアの方が、全体の事を考えてる分マシなのかもしれません(まあ、愚痴るだけで終われば同じことなんですが)。

あとは最近だと、「AI が作っちゃうのでよくわからないままスキル習得に終わってしまうケース」なんてのもあるのかもしれません。

どうあれ「個々の技術を磨きながら、全体を設計する能力も磨く」という事を阻害してしまっています。

ダメな設計はなぜ生まれてしまうのか

どこかの銀行のシステムの例を挙げるまでもなく、ダメなシステム開発と言うのは大小いっぱいあります。FPGA用の回路設計だって例外ではありません。

多くのダメなシステムは、正しい最終イメージがアーキテクトの中で出来上がっていないのに、部分から作っていって破綻するようなケースが多い気がします。

全体を見せてもらえない/全体を見る能力がない、などの制約下で、とにかく部品を作ってくっつければなんか出来上がるだろう(というか闇雲でもなんでも前に進む以外にやれることがない)、ぐらいのノリでどんどん作ってしまったんじゃないかと言うぐらい行き当たりばったりでカオスなシステムと言うのは、まあ残念ながら世の中にあります。

要するにグランドデザインがちゃんと出来ておらず、ゴールがどこにあるかあいまいなまま作っているので、ゴールまでにあと何を作れいいのか、どちらに向かえばいいのか、あとゴールまでどれぐらいかかるんか、などがわからないまま、目の前にある課題だけが課題として上がっていく状態です。

で、作った部品の数だけで進捗管理してるから、100個作ったのにくっつけても動かない状態になった後は、進捗率が 99% のまま工数がどんどん伸びていくというあの状態ですね。納期を過ぎた後、ひたすら疲弊しながら人海戦術デバッグして、ぎりぎり60点の合格ラインで納品するわけです。

逆に、正しい最終イメージが頭に描けるだけのスキルのアーキテクトが居る場合、あとゴールまで何が足りていないのかちゃんと把握できますし、仮にゴールが見えていない場合も ゴールが見えていないというリスク を正しく認識できるので、ゴールの位置を確認するための作業 なども正しく計画に組み入れていけるわけです。優秀なアーキテクトの居る組織ではおおむね 80点ぐらいのシステムを毎回きっちり約束通り仕上げていきますし、そのような組織の中で適正のある若者の中からは次のアーキテクトも育っていくわけです。

美しい設計はなぜ生まれるのか

ここで、経済的合理性は一旦おいておいて、100点に近い設計を考えてみます。

建築にせよ、機械にせよ、ソフトウェアにせよ、半導体プロセッサにせよ、美しいと思える設計 というのは少なからずこの世に沢山あります。美しいものはシンプルです。美しいものは機能性が高いです。美しいものは長持ちします。美しいものは時代を超えて美しいです。

もはや、お金の為に作るというよりは、匠がある種の芸術の領域に片足突っ込んで、自己満足の為に作らないと作れないような領域なのかもしれませんが、まあ確かにそういうものはあるように思います。

そして経験上、美しい設計を作っているアーキテクトは、驚くほどなんでも知ってるし何でも良く見て ます。例えばプロセッサアーキテクチャ設計で巨匠と言われるような人たちは、トランジスタレベルのロジック構造から、演算器やキャッシュの構成、メモリの特性まで熟知して、それらも極めてタイトでピーキーな部品として設計できる能力まで有した上で、最新のAIの学習モデルから半導体製造工程まで熟知してて神業みたいなアーキテクチャを設計しています。

私なんかは見ていてポーカンとなるだけなのですが、ほんと凄い人たちは凄いのです。

ここでおもむろにハッカーと画家ミケランジェロがシスティーナ礼拝堂の天井画の全ての像を自分自身で描くと 主張した話なんかをふと思い出したので、私見交じりに書くと、きっとミケランジェロの描く100点満点の作品には、100点満点の部品が揃っている必要があったのではないかなと想像してみます。

ここで言う100点満点の部品とは、例えばプロセッサを作る場合、そのプロセッサアーキテクチャ用に専用部品を作れと言ってるんじゃなくて、拘りたい部分に関してちゃんとトランジスタレベルで無駄のない綺麗な設計になってる汎用部品たれという話です。

で、冒頭の話に戻りますが、芸術観点で拘ったシステムが作りたくても、商業として部品開発者の中には 60点の部品しか作れない人がどうしても含まれてしまいますので、ミケランジェロは一切合切そういう要因を排除して拘りたかったのかな、なんて考えてみたりもするわけです。

どうすればシステム設計力が身につくのか

小さなゴールを自分で置く

一番の王道はこれじゃないかと思います。大きなゴールは初めから置かれているケースがほとんどと思いますので、自分の裁量の範囲で自分の小さなゴールを置く事です。

特にソフトウェアでは、要望された仕様を満たす部品の設計や実装方法、アルゴリズム選択は無数にある場合が多いですので、自分なりのゴールを置いてより自己満足度の高い部品を作ることを心がけることだと思います。

何よりも自分でゴールを置くという事は、完成形をイメージするという事であり、なぜそれを選択したのか一つ一つに自分なりの理由を見つけ、開発中もあと何が足りていないのか考え、不足を埋めながらゴールを目指すことができます。

そして少しづつ、大きなゴールを任されるようにポジション取りをしていくという事が重要に思います。

趣味で設計する

で、実はこっちが個人的にはメインだった気もしていて、なかなか「王道でアーキテクトが育っていくような環境をずっと維持できてる職場」と言うのは決して多くはないです。

となると仕事と言う枠を気にせずに自分でオレオレアーキテクチャを設計してみるというのが実はとても重要な気がしています。いくらでも大きなゴールを置いて挑戦することができますし、失敗しても誰も困りませんし、面白いものが出来ればOSSで公開したり、ブログ記事を書いたりすればいいわけです(笑)。

なんでもかんでも自己責任と言われてしまうこのご時世、ある程度は職場に頼らずに自分のスキルには自分で責任を持たないといけないのかもしれません。 まあ、さすがに「この先この職場環境だと能力を活かす環境が来そうにないな」とあれば転職なども選択になったりもするのかもしれませんが。

研究開発の場合どうなのか

研究の場合、「まだ誰もやってない未知のことを確認する」というのがメインタスクになります。要するに「やってみないとわからない」ので「ゴールも分からないし、進捗管理何てできるわけないじゃないか」というのもまあ、一理ある意見かとは思います。が、一方で、だからこそアーキテクト的な能力が問われることも多い気がします。

研究を行う場合、必ず何らかの仮説をもって実験を行う事になります。実験の結果仮説があっていることもあれば間違っていることもあります。

一方で、仮説を立てた以上は、正しかった場合のゴールイメージは立つはずです。そして仮説が正しいことを証明するための美しいシステムとは何か、どうすればそこにたどり着けるかを考える事は、仮説が間違っていた場合の証明もまた最短で行う事になります。

研究を一連のシステムとして、研究計画を立てて進めていく際にもシステム設計力やアーキテクト力みたいなものは同様に問われてくるように思う次第です。

おわりに

今回もかなり抽象的な駄文にはなってしまいましたが、新しいものを作るときに「そのゴールを想像してグランドデザインができる能力」と言うのは、大小問わず、研究するにも開発するにも重要な事ではないかと思います。

一方でそれらの能力は 意識的に取りにいかないと身につかない し、悪い環境にいても身につかない ので、そうなりたいと思った人がそれなりに自分で自分を育てるという事をやらないと身につかない能力なんだと思います。

「馬を水辺に連れて行くことはできても、水を飲ませることはできない」ということわざがありますが、組織も簡単に育てられる人材じゃない気がしていますし、昨今の組織は自分で育てるよりも、即戦力を中途採用したがる時代になっています。逆に言えばアーキテクトを目指す人にはリターンの大きい時代ではあるかと思いますので、是非頑張っていただければと思う次第です。

(コーヒーブレイク) AIにSF小説書かせてみた

個人事業主になって間もなく1年ですが、初めてやってくる青色申告を前に必死に勉強しながら準備しております(まあ大半は 会計ソフトがやってくれるんですが、仕組みがわからないと安心できないのがエンジニアのサガでして)。

今、大学様と一緒に研究連携させて頂いて、論文の連名にして頂いたりとか、ぼちぼちそういう赤字の活動もしているのですが、商品にならないようなものもいろいろ試作したりしているわけで、こちらの制度 に該当するのではないかと思い、いろいろ調べたり、計算したりしていたのですが、結局1日費やしてしまいました。

freee会計を使っているのですが個人事業主向けの安いプランだとこの申告は未対応で、やるなら自分でやる必要がありそうです。 法律系の条文を読み解いて計算するというのは、エンジニアにはなかなか難易度が高いですね。

幸い今はAIがあるのと、私の父が役人だったのである程度こういう条文作ってる方々の裏側の苦労とかも多少の見聞きはしており興味は持っていたので、いい勉強にはなりましたが、金額が小さすぎて申請をためらうレベルだなとか思いつつも、正しく税金計算して納税するコストってて案外大きいな と改めて。

そして、もうちょっと理系向けの数式で表現したり、機械的に最適化したら、少しぐらいマシになったりしないものなの? なにより もう全自動で徴税してほしい というフラストレーションを感じてみたりもしつつ。

ということで、今日、いっそお金のない世界で全部アルゴリズムに支配してもらえないの?、といったホモ・デウス に出てくるような話を AI に愚痴っておりましたら、何やらSF小説が出来てしまったので張っておきます。

いろいろ注文つけて、星新一さん風に仕上げてもらいましたが、いやはや生成AI に、コード以外にちゃんとなにか生成させたのはじめてかもです。

戯れに置いておきます。


タイトル:『完璧な収支』

 エヌ氏は、窓辺に届いたリンゴを手に取り、その艶やかな皮を眺めた。  この世界には、「お金」という言葉も「金額」という概念もない。あるのは、膨大な計算機網が編み上げる、巨大で精密な「あみだくじ」だけだ。

 エヌ氏が一篇の詩を書く。その所有権が網に吸い込まれた瞬間、彼は夕食のリンゴと、冬を越すための軽油を手に入れる。  詩を欲した誰かのニーズが、リンゴを余らせていた誰かのニーズと、一瞬で、物理的に直結したのだ。そこには、情報の不透明さを利用して、見えないコストを上乗せする仲介者の入り込む余地などなかった。

 「実に気分がいい。昔の人は、不自由だったらしいな」

 エヌ氏は、古びた資料で読んだ「税金」という奇妙な制度を思い出した。  かつての人類は、リンゴを買うためにまず「円」という名の数字を集め、さらにその中からいくらかを「納税」として差し出していたという。役所という建物に人々が集まり、「確定申告」なるパズルに頭を悩ませる。払いすぎた、足りない、計算が違う……。そうして集められた数字が、本当に目の前の道路に使われたのか、誰にも分からなかったのだ。

 しかし、今のアルゴリズムは冷徹に、そして誠実に働く。  エヌ氏が散歩に出れば、一歩ごとに「道路の摩耗代」や「街灯の明かりの代金」が、彼がこれまでに提供した価値の「貯蔵分」から、一滴の無駄もなく、リアルタイムで差し引かれていく。  申告も、徴収も、着服もない。世界は完璧な「等価交換」だけでメンテナンスされているのだ。

 「さて、残りの分を確認しておこうか」

 エヌ氏が端末を操作すると、彼がこれまで積み上げてきた「貯蔵リスト」が表示された。  そこには「米一トン」「石油五百リットル」「最新の治療薬へのアクセス権」、そして「純金十グラム」といった、実体のある価値が並んでいる。  これらはアルゴリズムが、世界中の倉庫や工場で常に「エヌ氏の取り分」として確保している権利だ。たとえ明日、何らかのシステムトラブルが起きても、この「実物」へのアクセス権が消えることはない。

 「これで老後も安心だ。私が若いうちに提供した価値は、こうして腐らない形で世界にストックされている。何しろ、『仲介』という名目で複雑な手数料を差し引く、得体の知れない管理者を介さずに済むのだからね」

 散歩の途中、エヌ氏は資料にあったもう一つの、最も理解しがたい記述を思い出した。  『金利』と『インフレ』という現象だ。  昔の人々は、何も生み出さず、何も提供していないのに、銀行に預けておくだけで数字が増えることを期待したという。その一方で、誰かがどこかで数字を刷り増やすと、昨日までリンゴ一個と交換できた数字が、今日は半分しか交換できなくなる……。

 エヌ氏は思わず足を止めた。  「何もしていないのに数字が増えたり、何も使っていないのに価値が減ったりするなんて。それはまるで、物理法則を無視した幽霊の仕業じゃないか」

 実体のない数字に魔法をかけ、人々の労働を吸い取る。そんな、論理が崩壊した呪術のような世界で、彼らは正気を保てていたのだろうか。

 エヌ氏は、リンゴを最後の一口まで味わった。  ふと見ると、足元の舗装路が、ほんの少しだけ輝きを増した。  エヌ氏が今朝書いたコードが、どこか遠くの道路補修システムの効率を向上させたらしい。その「お返し」として、彼のリストに、新たな「高級肥料の優先権」が一つ付け加えられた。

 「なんて素晴らしい、合理的な世界だ」

エヌ氏は満足して歩き出した。  そこには、銀行も、税務署も、証券会社もない。  ただ、人々が互いに差し出した「価値」と「感謝」が、目に見えない網となって、どこまでも美しく、公平に広がっているだけだった。



(感想とか)

AI面白いこと書くな、と思いつつ、昨今の米価格の騒動とか見てると「適正な価格って何」なんてことは考えさせられてしまいます。

おにぎりが一個あったときに、それは間違いなく「おにぎり美味しい」という体験とともに「おにぎり一個分お腹が膨れる」という価値を提供してくれるわけで、安く買えても、テンバイヤーから倍の値段で買ったとしても、そのモノ自体の価値は変らないわけです。

小説の世界は、ニクソンショック前の金本位制の時代とか、加賀百万石とか言ってた江戸時代とかの価値観に近いのかもしれません。

たぶん真逆の世界観としては、すべての価値をお金で支配する世界 で、例えば政府が紙幣発行をやめて、アクセスコントロール付きのトークンとしてデジタルマネーだけを発行し

  • 発行量を自在に調節してお金の価値を上げ下げする
  • 消費を加速するためにお金に消費期限を付ける
  • 一日の利用額を制限する/犯罪者の資産を凍結する

などなど、お金を支配することで世界を支配する世界でしょうか。

最近でも、現金で買うよりローンにしてその分NISAに入れた方が得、みたいな、モノに目が行かずお金で損得を考えてしまうパターンは増えているのですが、「いい車に乗りたい」とか「美味しいもの食べたい」とかモノや体験そのもの価値と、「今日も一日頑張って働いた」という達成感を、もう少しダイレクトに結び付けられる思考方法もあっていいのかなと思って見た次第です。

リアルタイムAIで考える事

はじめに

当サイトでは、応答時間がミリ秒以下になるような、高リアルタイム性のコンピューターシステムを検討対象としており、AI(というか機械学習)もその対象範囲です。

このようなリアルタイム性の条件下でAIを考える場合、通常の AI のように単に高精度な結果を出せる学習モデルを設計するだけではだめで、時間経過の中で今出力できる最善の解に更新を繰り返していくモデルを設計し、 実世界のダイナミクスに追従する適応性 を持たせることが必要になります。

ですので今日はあまり一般的な話ではなく、この分野に閉じて、少し考察をしてみようと思います。

メモリ階層とモデルの矛盾

一般的な計算機のメモリは階層的になっており、CPUなどでも1次キャッシュから3次キャッシュ、外部SDRAMなどの階層で、容量が小さく高速なものから順に、大容量で低速なものになっていきます。

FPGAなど、自由に計算機アーキテクチャを設計できるデバイスにおいてもこれは同様で、利用できる演算資源としては、階層的になっており、例えば以前に下記のような絵を描いたことがあります。

リアルタイムコンピューティングのメモリ階層

一方で、リアルタイムコンピューティングでは、新しい入力から出力更新までの制約時間の中で読み出せる量のデータしか使えません。 例えば サンプリングレート 1kHz (1000fps) で1ms (1ミリ秒は 1000分の1秒) で応答する処理を行う場合、メモリがどんなに大容量であっても 1ms で読み出せる量のデータやパラメータしか演算に投入することができません。

そうすると、大容量メモリほど少しのデータとパラメータしか使えない という一見矛盾したことが起こり始めます。

容量と速度の逆相関

しかしこれはとても重要なことで、同じくリアルタイム処理であるグラフィックスレンダリングの処理などでは、例えば 60fps でゲーム画像をレンダリングしたい場合、16.6ms で読み出せるデータ(テクスチャやポリゴン頂点など)しか描画に使えません。 そうなると容量よりもデータ帯域が重要となり、GPUには GDDRメモリなど容量は少ないが高速なメモリが採用されてきた歴史があります。

高リアルタイムシステムほど、これのもっと極端なことが起こっていきます。

ではそのような制約下でどのようにAIモデルを考えていくかと言うのが本記事の考察です。

階層メモリのリアルタイムでの活用方法

それではパターン別に大容量メモリをうまく使う方法を考えていきます。大きくはデータの履歴(状態変数も含む)の保持に使うパターンと、学習パラメータを置いておくのに使うパターンとがあると思います。

データ履歴の活用の工夫

最初に過去のデータを利用する観点で考察します。今入力されたデータだけでなく、過去に入力されたデータを使う事で、空間的な広がりや、時間的な変化を認識できるようになります。

データの古さで置き分ける

もっともオーソドックスな使い方がこれでしょうか。例えば画像処理においては

のようにすると、空間と時間の3次元方向の周辺情報を使ってそのピクセルを処理することができます。 画像のようのものは1フレーム自体が巨大ですし、場合によっては何フレームも過去の情報を使いたい場合は容量の多い外部メモリを活用できます。 内蔵メモリにフレーム全部が収まらないにもかかわらず、カメラデータ入力の数倍程度のメモリ帯域があれば、演算対象のピクセル周辺のデータは常にオンメモリに持ってこれる構成が作れます。

状態空間モデルで、各ピクセル位置に状態を持たせる場合でも、状態変数をフレームと一緒に外部SDRAMに記憶して、次にそのフレーム位置が来た時に状態を復元して、次の時刻の計算を行うのも合理的な使い方と言えるでしょう。

特に周期性を持った時系列処理においてこの考え方は非常に重要で、例えばお店の売り上げのような時系列データでも、曜日や季節に影響を受けるため、昨日の同じ時間、先週の同じ曜日、先月の同じ日、昨年の同じ日、などとはしばし比較評価を行います。 大容量メモリが大量の容量を持っていることを利用して、ピンポイントで古い情報を利用するのに利用するわけです。

お店の売り上げの例だとあまりにも長いですが、我々の身の回りや、産業応用などでは、エンジンの回転周期ぐらいの周期性を持った時系列は沢山あります。特に人間には感知できないぐらい高い周波数でも計算機なら感知できるというのは重要なことだと思います。

選択的に履歴を選ぶ

履歴はそのままフラットに記録しておき、どこを読み出すかを選択的に選ぶことで読み出しデータ帯域を抑えることもできます。

以前に、ハイフレームレートでは動き補償の計算が激減できるという話をしたことがありますが、該当するピクセルに写っていた物体が、過去のフレームのどこにあるか追跡しながらそこだけピンポイントで取り出してくることもできます。

例えばバイクに乗って手を振っている移動している人から、「手を振っている」という時間変化成分を加えてた認識が、限られたメモリ帯域の中でできる可能性など出てくるわけです。

動き補償は極めて強力な武器で、60fps で 16ピクセル移動する物体でも、1000fps なら1ピクセルしか移動せず、CNN の3x3の畳み込みフィルタに収まってくれます。

また ViT などの応用で、画像の中の注目すべきポジションを計算して、次のフレームでそのあたりを重点的に読み出すのも手です。

これもリアルタイムシステムであれば、1ミリ秒の間に最大で何ピクセル移動するかは、物理的に制約できる事が多いですので、対象のダイナミクスにあわせてマージンを設定すればよく、効果的に過去のデータを限られた帯域の中で活用できます。

過去の情報を要約(圧縮)して使う

これには時間方向の要約と空間方向の要約の2つの軸があると思いますが、読み出し時ではなく書き込む際にデータ量を圧縮してしまう方法です。

いずれも要らなくなった情報から順に削除したり圧縮したりしていきます。 例えば古いものを 1/2 に出来れば、 1/2 + 1/4 + 1/8 + ・・・ = 1 ですので、決まったメモリ帯域の中で履歴にアクセスし続けられる計算になります。

例えば以前に単純に画像を縮小していくというMIPMAP方式を提案したことがあります。 Attention 的に有用なものだけ残す手もありますし、また、認識まで行ってもっとメタ情報として圧縮する方法もあるでしょう。

縮小を行うと1つのピクセルの処理において、より広い範囲を俯瞰して判断することが可能になり認識精度が上がります。

画像処理では認識したい画像特徴に対してスケール普遍性がある場合が多く、画像ピラミッドを作って認識することは多いです。 CNNなどでも特徴量の世界でもこれは同じであり同じ認識器をマルチ解像度に適用していくのは合理性があります。

また動き補償と縮小とを組み合わせると、把握できる範囲が 6x6、12x12、24x24 ・・・ と倍々で広がりますので、多少の移動速度であれば簡単にスコープに捕らえます。過去の動きは大雑把に追跡して、最新位置を最新の最大解像度の画像で正確に認識し、さらにその情報を次のフレームに状態として引き継げるわけです。

パラメータ利用の工夫

昨今のAIでは 入力データよりもパラメータの方がはるかに巨大 ということがしばしあります。

すべてのパラメータがFPGA内などにオンメモリにもてれば何の苦労もないわけですが、残念ながら外部SDRAMなどにパラメータを置いておいて動的に入れ替えなければ、極めて小パラメータのモデルしか使えないことになってしまします。

パラメータを動的に変更する

例えば、高速に応答したい物体Xの認識パラメータセットと、その他の認識対象セットがA、B、C、D・・・ と何セットかあった場合

X → A → X → B → X → C → X → D → X →

のようにタイムスロット(画像なら1フレーム毎とか)ごとにパラメータセットを入れ替える手が考えられます。

1つのタイムスロットで読み込めるパラメータ数は決まっていますので、時間ごとに切り替えることで、見逃せない X を頻繁に調べつつ、他のものも探索するようなことは十分にあり得ます。

100クラス認識できるものを 10 回入れ替えて 1000クラス分類に近づけていくようなアプローチでしょうか。

選択的にパラメータ使う(MoEなど)

MoE(Mixture of Experts) も最近よく耳にする技術になってきました。これはもちろんリアルタイムAIでも重要な要素だと思います。

画像認識も、街中や森の中、夜間や霧、顕微鏡画像やMRI画像など、環境の違いもあれば、認識したいものが人間だっり、自動車だったり、交通標識だったり、部品のひび割れだったり、病気の腫瘍だったり様々です。

これらをパラメータセットを沢山持っておいて、適応的に切り替えながらあらゆるシーンで活用することを考えるのも、限られたメモリ帯域を有効に使う上でとても重要です。

例えば、人間が前を向いた時、横を向いたとき、後ろを向いたとき、などそれぞれを学習させた認識器を使って、今どういう運動をしているかを認識しておけば、次のフレームでロードすべき認識パラメータはおのずと決まってきますし、変化や状況を見て適応的に次にロードするパラメータを選ぶことで、一度に使うパラメータ数を抑えながら幅広い認識を応答性良く行える可能性が出てきます。

ハイブリッドに使う

ここまで挙げたようなテクニックをハイブリッドに組み合わせることももちろんありだと思います。

特に、センサーの値を特徴量として汎用的にとらえる部位と、特徴量から目的に合わせた認識を行う部位はしばし分けて考えられます。

特徴量を作る部分では、例えば昼用と夜用などシーン変化に応じてパラメータを切り替えて常に高品質な特徴量を得られるようにして、後半は認識対象に応じてパラメータを切り替えるような手もあります。

100クラスのうち50クラスだけは常に同じものを認識するようにして、残りの50だけを変えたパラメータを入れ替えるなどもありでしょう。

用途にに応じた組み合わせこそが重要だと思います。

おわりに

アルゴリズム開発をしている多くの人にとって、0.1 秒で以下で終わるものと言うのは、どれも大差ないように思えるかもしれません。

一方で我々の生活するリアルな空間では、その 1/100 である 1ミリ秒(0.001秒)であっても、案外大きな変化をします。 人間は 100mを10秒 (1m を 0.1 秒)で走ってしまう生き物で、時速何百キロのボールを投げることもできます。 一般人がその半分の速度で動いても 1ミリ秒に何cm も移動するのです。

また、人間は応答に 0.1秒以上かかると言われています。ですので人間をアシストする計算機まで 0.1秒遅れてしまうと遅延が倍になります。計算機がアラートを出してから人間が回避行動をとるシステムにしたら 2倍鈍感な動作しか出来なくなった では悲しいわけです。

近年では フィジカルAI とか エンボディドAI と言われている領域の中には、これらが課題になる分野が間違いなくあります。

そしてこれらの分野にむけて学習モデルを作る場合、単に総演算量だけ考えればいいものではなくなります。

アルゴリズムを1ミリ秒などのタイムスロットで細切れにして、どこにどのようにデータを置いて、タイムスロット間では何を渡して、システム全体としてどう振舞うようにするか、を考える必要が出てきます。

考える事が一気に増えて複雑なパズルを解くことになりますが、これは好きな人にはとても楽しい話ですし、新規性のある独自の工夫や、他の方式との差別化がとてもやりやすい領域になります。

昨今の FPGA は、学生が研究用に研究室で買ってもらえるぐらいの価格帯のFPGAで、 ResNet18 を 60fps で動かせる程度の演算リソースは内蔵するようになってきました。これを 60fps の 16.6ms で計算するのではなく、 1/16 の演算量の計算を 16回に分けて行うことで、定常的には従来相当の認識率を保ちつつ、変化に対して 1 ms などの応答性を持たせることが出来れば大変興味深い研究になってきます。 最初の認識に 16ms (16フレーム)かかっても、それは従来と同じですので、そこから先に 1ms の応答性が手に入るなら大きな進歩を手に入れたことになります。

もしこういった分野に興味のある方、是非、いろいろ考えてみて頂けると面白いのではないかと思います。

フィジカルAIについて考えてみる

はじめに

昨今、フィジカルAIや、エンボディドAI などの単語をよく聞くようになってきました。

当サイトのリアルタイム性に対するこだわりが発揮しやすそうな領域であり、FPGA 応用の生きてくる分野でもありますので、少し考察してみたいと思います。

昔からあった領域に新しい名前が付いただけと言う部分も大いにあろうかとは思っておりますが、分かりやすい言葉で一般の人に周知されるという事は非常に重要な事ですので、大変喜ばしい方向に進んでいるように思います。

何より、数千億円規模の大規模GPU環境で学習した LLM が群雄割拠している中で、弱小企業や研究機関や個人が太刀打ちしようとすると勝負の土俵を変えるしかない部分はあり、そういった中で、日本にある、まだ学習につかわれていないデータや、データ化すらされていない技能などをターゲットにしていくのは、戦略としてはありだと思うわけです。

FPGAによるフィジカルAI考察

リアルタイム性での分類

フィジカルAIの類は、基本的には IoT でありエッジコンピュータの存在が前提になると思います。エッジコンピュータはリアルタイム性以外にもセキュリティーの問題だったり電力の問題だったりいろいろな観点で分類がありますが、当サイト的には、リアルタイム性の観点に絞って考えます。

そうすると大雑把に

  • AI をクラウドに投げても良いケース [ノンリアルタイム]
  • ノンリアルタイムOS上で動くGPUでよいケース(Jetsonなど) [数十ミリ秒の応答+ミリ秒単位ーのジッタ]
  • リアルタイムOS+NPU などで頑張るケース [サブミリ秒オーダーの応答+マイクロ秒単位のジッタ]
  • FPGA を使うケース [マイクロ秒オーダーの応答+ナノ秒単位のジッタ]

ぐらいの区分を思いつくわけです。

正直、9割ぐらいは「Jetson で十分」という領域かとは思っておりますが、1割ぐらいは FPGA でこそ開拓できる分野があるのではないかと思っています。

FPGAでしかできない低遅延AI計算

例えば産業用のサーボモーターは 1k~100kHz ぐらいの周期で電流量を変化させているわけですが、たとえばこれを「強化学習によってAIで制御してみよう」なんてことは発想としてはすぐ出てくるわけです。

センサーとしてもIMUとか圧力センサとか一エンコーダとか色々なものが利用可能ですが、例えば当サイトがやっているカメラ画像処理での1ミリ秒でのAI認識とか、1ミリ秒後に視界の変化捉えるオプティカルフロー演算の結果を出すみたいなものも応用範囲に入ってくるかと思います。

こちらなどでも書きましたが、GPUは同じ計算の並列実行を行わないと性能が出ませんので、コア数に応じて何千とか万とかのオーダーでデータを溜めてから演算を開始しないと性能が出ません。 従って原理的にどうやってもメモリに溜める遅延時間を許容しない限りAI演算性能を発揮できない宿命にあります。さらに GPU の多くは Linux などのノンリアルタイムOS上で動くことを前提としています。最近は Linux のリアルタイム機能も充実しては来ていますが、GPUへのデータ転送やキャッシュヒットのバラツキなどでどうしても計算時間に大きなジッタが出てきます。

そうすると、ある程度の大容量のAI計算をリアルタイムにやろうとするとFPGAに利が出てきますし、FPGAにあったパイプライン計算での演算や、データフローを乱さず低遅延で出力できる学習モデルの開発が重要になってきます。

まず試作しないとデータすら取れない領域

そして何よりここからが重要なのですが、低遅延でリアルな対象を相手にすると、FPGAなどで試作しないとデータすら取れない という事が起こります。

ロボットなどは専門ではないのですがわかりやすいので、例えば「風の中でカメラ画像を見ながらバランスをとってキャッチボールをするドローン」みたいなものを考えてみます。

そうすると、非常に乱暴に言うと、姿勢制御をしながら飛んでくるボールに向かうように、「次の瞬間の各モーターの電流値を決めるAI」を開発したいという話になります。

この際にとても厄介なのが、出力如何で次のセンサー値も変わってしまう という事です。モーターの動き如何で視点となるカメラも移動してしまいますから。

近代のAIのほとんどは、取得済みのデータセットを固定された入力として用いて学習していますが、フィジカルAI分野では AI の学習次第で入力も変化する という事が起こるわけです。

CGなどのシミュレーション(ある種のデジタルツイン)でもある程度補完できるケースもあるかとは思いますが、そのシミュレーションを作るための基礎データは、「実機でリアルにフィードバックして何が起こるか」というデータを集めない事には何もできないわけです。

そしてそのデータ自体も、「マイクロ秒単位でフィードバックを掛けて初めて起こる事象」のデータなわけですから、低遅延計算をまず試作しないと何の実験も出来ないわけです。

逆に言うと、そのようにして作られた学習データや学習モデルはまだ世の中にない唯一無二なものですので、十分に、世界初/世界一を目指して研究開発できる魅力的な分野になってくるわけです。

フィジカルだからだからこそのリカバリの効く領域

もう一点、フィジカルAI 分野で、特に、kHz 以上の高サンプリングレートで起こりがちな面白い事象として、リカバリが効く というのがあります。

人間が1本足でバランスを取って立っているようなときに、ふらふらしながらバランスを取りますよね。 ロボットなども同じで、あるマイクロ秒時間で予測を間違えて電流を止めてしまったり流しすぎたりしても、次の瞬間にそれを打ち消すだけ電流を流すとごまかせるなんてことは普通にあります。確率的にON/OFFを繰り返して結果をフィードバックしながら微妙な制御をするというのはルールベースでもいろんなところで行っていることです。

モーターに限らず、PWMで作る光の階調や、D級アンプの音声などでも、そもそも人間の感度より高い周波数でON/OFFを繰り返してますので、最終的に人間が感じる積分値が同じになるように後から多少のリカバリが出来たりもします。

要するにシステムにもとからある程度のマージンがあり、実行時にマージン範囲内で試行錯誤ができるという事です。 これは、学習モデルを考えるうえで、間違った答えを出すと一発アウトな従来AIと大きく違うところだと思っております。

また、このマージンを使って、実働中に「微かな試行錯誤」を行い、実働中に賢くなるAI(いわゆるオンライン学習)のようなものを入れ込む余地なども出てくるのではないかと思います。

製造分野などでも不良品にならない適正値の範囲では当然どんな製品にも微小なバラツキはあるわけで、要は最後にばらつきを規定範囲に収めることが目的なわけです。

おわりに

当サイトでは、計算機科学の観点、特に FPGA を起点に、フィジカルAIを眺めております。

AI の良いところは、ルールベースで手に負えなかった部分を扱えるようになった点だと思います。

我が国においては、すでにこの分野は非常に高いレベルで制御工学が発達しており、ルールベースのシステムが多数稼動していると思います。それらの中にAIを入れ込むというのは容易でない部分もありますが、うまく共存しながら拡張としてAIを足しこめれば大きな変化をする分野もあるのではないかと思います。

先のサーボモーターの例を挙げましたが、他にも高速回転するエンジンの点火タイミング制御とか、人間の四肢や視覚/聴覚などの拡張であったり、医療、宇宙までいろいろな研究対象がありそうに思います。

ビジネスの観点でも、製造装置のようなドメイン固有の技能のAI化であったり、汎用ロボットとか人間の拡張(パワードスーツとか電脳メガネとか)のような多目的に使えるAIまで、まだまだ未開拓な領域が広がっているように思います。

AI を研究テーマにしたいという若者の方も増えているかと思います。一方で、パソコン上で Python 使ってできる範囲で論文書いて学位取ろうとすると、やってる人が多すぎてテーマ選びから苦戦するという方も多いと思います。

幸い今フィジカルAIというワードがちょっとしたバスワードになっていて、昔なら「単にFPGA化しただけでしょ」としか見られなかった分野が再注目されているわけですから、FPGAやってみたいなと言う方に興味を持っていただけると嬉しく思う次第です。

もちろん「リアルタイムに動くシステムを試作する」と言うのはそれ自体結構大変ですし、「自分で作ったシステムに適した学習モデル」を考えたり、「実際に学習させたり」はとても大変なことではあるのですが、苦労に見合った楽しさや見返りはある分野だと思っております。

VLIWとスーパースカラについて考えてみる

はじめに

少し前に SIMT であるGPUの話 とか SIMDを持ったCPUの話 とか書いてきました。

MIMD についても考察しないといけないなと思いつつ、先だって頭の中で VLIW について気になり始めたので、引き続き個人的な見解を書いてみたいと思います。

また、命令実行方式の違いはあれど、データフローは VLIW と スーパースカラは良く似ているので合わせて考えてみたいと思います。

VLIW(Very Long Instruction Word)

VLIW というと、IA-64 (Itanium) を思い出す方も多いかもしれませんし、トランスメタ社の Cursor を思い出す方もいるかもしれません。最近だと Qualcomm Hexagon が割と成功しているようです(触ったことないですが)。

また 筆者が知っている範囲ですと、AMD の Versal や Ryzen で利用されている XDNAVLIW だったと思います。

VLIW はその名の通り、複数の命令を束ねて1つの長い命令を実行できるようにしたものです。 身も蓋もない言い方をすると、近代のCPUがスーパースカラによる並列実行を行う際に性能を出すためのアウトオブオーダー実行機構などを、CPUがハードウェアで実行時に行うのではなく、プログランのコンパイル時に静的に行おうというものです。

必然的にプロセッサの内部構造が生々しく命令セットに反映されがちですので、バイナリ互換性をどう保つか が一つの重要なファクターであり、互換性を無視して使うケースでの VLIW は普通に実用的だと思います(都度都度コンパイラ作る人はたまったもんじゃないのかもしれませんが)。

一方で、「バイナリ互換性を保ったまま、将来並列性を拡張したい」となると途端に難易度が上がり、「プロセッサの並列数が変わっても互換性のある、並列命令ってどうするの?」という素人目に難しい話になるように思います。

たしか Itanium では命令の並列数を固定せずに、並列実行できる区切りだけを与える命令フォーマットにしていたと思いますし、Cursor では、コードモーフィングによって x86 命令から変換する事で次の Efficeon に拡張しようとしました。

が、結果的に、ハードウェアで変換する今の x86-64 が一番柔軟性があって性能が出て生き残ってしまったという歴史になっているように思います。

一方で、おそらく今の x86 の内部で μOPS を実行する部分は VLIW みたいなものにはなっている気はします。

ソフトウェアパイプライニング

さて、命令セットの問題を置いておくと VLIW にせよ スーパースカラにせよ、異なる命令を同時に実行する と言う点では同じです。 SIMDやSIMTでは同じ命令を同時に実行することしかできませんでした。

しばし当サイトではFPGAの得意な処理として、データ並列の対局としてパイプライン並列の話をしてきましたが、まさにそれが可能でして、ソフトウェアパイプライニングなどと呼ばれます。

これはコンパイラで自動的に行われたり、実行時にアウトオブオーダー機構がいい感じにしてくれたりすることもありますが、明示的に書くなら下記のような感じです。

// prologue
a0 = x[0];

// pipelining
for (i = 1; i < N; i++) {
    a1 = x[i];
    b0 = a0 * 3 + 1;
    y[i-1] = b0;
    a0 = a1;
}

// epilogue
y[N-1] = a0 * 3 + 1;

で、どういう事が起こるかと言うと、下記のような事が起こることを狙っていくことになります。

ソフトウェアパイプラインの狙い

ここでは、あるデータを Store Unit で書いているときに、加算器で次のデータを加算しつつ、その次のデータを乗算器で乗算しつつ、さらにそのまた次のデータを Load Unit で読んでくるという、パイプラインができます。

規模こそ限定的ですが、以前 こちら で発表させて頂いたような動きが CPU でも出来てしまう事になります。

複数の異なる動作ができる実行ユニットを並列実行できるVLIWやスーパースカラ計算機だから出来る事で、特筆すべきことだと思っています。

もっとも、ほとんどの実行ユニットは1サイクルでは処理が終わりませんので、実際にはもう少したくさんのデータで各実行ユニット内のパイプラインの深さを埋めることになります。

1命令で4つずつデータを処理する MN-Core は、非常に合理的に出来ている VLIW の一つだと言えるのではないかと思います。

おわりに

SIMD や SIMT ほど長い話にはならなかったですが、異なる命令を並列実行できる と言う点は、並列化の難しい多くの複雑な問題に対して非常に有効に機能すると思われます。

一方で並列化の規模や粒度の点で、アウトオブオーダーのスーパースカラは命令デコードの負荷から限界があると思います。

しかしながら、「バイナリ互換性を求めないVLIW」であればまだまだ発展の余地がありそうにも思います。

いずれにせよ、同時に異なる演算を実行できる という利点を最も持っているのは FPGA だと思っておりまして、以前、「FPGAは1命令を繰り返すVLIWプロセッサ?」という記事を書かせて頂いた話に繋がるわけです。

世の中で何か面白いアイデアが生まれてくることを祈りつつ、筆をおきます。

(おまけ) 続・FPGAに対する誤解

はじめに

前回、FPGAに対する誤解と「どうFPGAを使うべきか」 という記事を書きました。

ちょっと調子に乗ってアンチパターンをイラスト化してみたのでおまけ記事として書いておこうと思います。

本来のFPGAの活用シーン

本来のFPGAの活用シーン

ISPなどの典型ですが、例えばカメラから入ってきた画像を入ってきた順で処理して、そのまま出力するのでとても効率的です。

従来は画像の現像や高画質化処理ノイズ除去などが一般的でしたが、当サイトではこのやり方で「動き計測」とか「AI認識」など、いわゆる CV(Computer Vision) と言われる領域に手広く適用可能であることがだいぶ示せてきていると思います。

CG分野でもこのアーキテクチャでの低遅延ポリゴン描画など示せてきました。

アルゴリズム研究者が使う環境

便利な並列計算機であるGPUの為に、一度データをメモリに溜めて並列化することで並列演算を可能にするように構成したものです。 最先端の半導体製造プロセスで作られた高速大容量の計算能力の恩恵に預かりやすいです。

アルゴリズム研究者が使う環境

画像処理アルゴリズム研究の分野では、多くの領域でAI(深層学習)を使った研究が、特に認識精度(accuracy)の観点で SOTA(state of the art) となっていきました。 必然、非AIの研究はしばし「AIと比べて性能で勝てるの?」と言われてしまう辛い時代になりました。

遅延や電力やコストを置いておけば、GPU上で机上でアルゴリズム精度の研究を行うのは非常に便利ですので、この形で研究されたアルゴリズムが世にあふれることになりました。

もちろん一度メモリに溜めた分遅延は増えますし、コストや電力も増大しますが、「簡単にアルゴリズム実験がいろいろできる」という効率性の前には些細な事です。

これはこれでもちろん世の中をすごく進歩させてくれたのですが、計算機は とにかく AI 性能がいいことだけを求められるようになってきました。

また、遅延等が課題になる分野の研究が置き去りになってしまうという、困ったことも起こっていると思っています。

誤解1:GPU計算をそのままFPGA化してしまうパターン

で、前回記事の続きで、GPU方面からFPGAに興味を持って下さった方が、陥る可能性のアンチパターンその1です。

GPU計算をそのままFPGA化してしまうパターン

FPGAにする(というかハードウェア化する)と高性能化する」と聞いて、今あるGPU用のプログラムをそのままFPGA化しちゃうパターンですね。

往々にして最先端プロセスで作られ、大量の浮動小数点演算器のハードマクロを持ち、GDDRなどの高速メモリを持つGPUに、汎用ロジックで勝てるわけがなく、苦しむことになります。もっとも計算機の勉強にはなると思います。

誤解2:そのままそこだけストリーム化してしまうパターン

そこだけストリーム化してしまうパターン

FPGAはストリーム処理が得意だと聞いて、そのままそこだけストリーム化してしまうパターンですね。

見ての通り、GPUの為に ストリームを並列データに変換してあるものを、再度ストリーム化するというもったいないことになっています。

とはいえ、「原理的には低遅延なリアルタイム処理に持っていけるアルゴリズム」が生まれてくる可能性がある点では、そこまで悲観的ではないです。

ただ、ストリーム処理は「演算器を再利用する」ことが苦手なので、しばし「リソースが足りなくて収まらない」という事になりがちです。

アルゴリズムを出発点にせずに、ハードウェアアーキテクチャを出発点にアルゴリズムを組み立てる という事が必要です。

考えて欲しいこと

冒頭のFPGAに適した処理は、実はアナログ時代の信号処理に似ています。 アナログ時代は、「信号をメモリに溜める」ということが極めて困難だったため、必然的にメモリによる遅延はありませんでしたが、できる演算に限りがありました。

一方で、デジタル時代ではメモリが使えますので過去のデータが自由に使えます。 (なお、未来のデータを使おうとするとそのデータが来るまで処理を遅延させることになります)。

これをアルゴリズムにうまく組み込むことが重要です。

冒頭の絵では入力が一直線に処理されているだけでしたが、下記のようにメモリを追加すれば、低遅延なストリーム処理に加えて、過去のデータへのアクセスが可能になります。

FPGAで効率よくメモリを使うモデル

AI で言えば RNN などのリカレント構造が作れるという事ですね。

以前「リアルタイムコンピューティングのメモリ階層」という記事を書き、こんな絵を載せました。

リアルタイムコンピューティングのメモリ階層

メモリ階層をしっかり考えて、アルゴリズムや学習モデルに反映させるというのは、リアルタイム性を高める上では非常に重要です。

おわりに

AIとGPUの台頭で、本来 FPGA が得意だったリアルタイム性の高い分野が、非リアルタイム分野で研究されていた画像処理研究からだいぶ置いて行かれてしまってているように思います。

  • 計算機アーキテクチャを勉強しないと太刀打ちできない
  • 難しいFPGAプログラミングを覚えなければ実験データすら取れない

などの壁はあるものの、これらを乗り越えれば

  • GPUのことしか考えていない人とは一線を課す新しいモデルの提案
  • みんなが使っているのとは全く異なるオリジナルなデータを使った研究

という差別化が可能です。

大事なのは本質がわからないまま表面的な理解でFPGAを使うと、余計な苦労をした挙句に成果が出ない、なんていうもったいないことになるので、よく理解して、作戦を立ててから使って欲しいという事です。 ちゃんとわかってしまえば、とても楽しいですし、レッドオーシャンで血の涙を流している研究者を横目に、前人未踏のブルーオーシャンを次々開拓していける事でしょう。

若い学生さん、研究者の皆様、FPGAは楽しいし狙い目ですよ!

私は研究者というよりはエンジニア側の人間ですので、「こんな研究があると面白い」という情報交換だったり、「こんな環境なら作れるよ」というったエンジニアリング側からのお手伝いしか出来ないのですが、新しくて面白い研究が生まれてくるのを楽しみにしております。そしてなにより、研究者の方々にも不毛な作業を減らし充実した日々を送っていただけれれば幸いに思う次第です。

FPGAに対する誤解と「どうFPGAを使うべきか」

はじめに

以前、FPGAを始めるときの壁 というのを書かせて頂きました。 また最近、CPUGPU についても幾つか個人的意見を書かせて頂きました。

今日は、今のところ私が最も熱を入れている FPGA について私見を書いてみたいと思います。

FPGA に対する誤解

今、特に GPU などで AI に取り組んでいる方々が「FPGAというデバイスがあるらしい」と興味を持ってこの分野の門をたたいてくださる機会が増えているように思います。

一方で、高価なFPGAボードを買ってきて、ものすごく苦労してベンダーの出しているツール(AI開発ツール含む)を覚え、慣れない難しいプログラムのデバッグに翻弄され、GPU の 10倍も100倍も苦労して作った挙句、GPU の 1/10 も性能が出ず、性能も電力もコストもリアルタイム性すらGPUに負け、いいとこなしで「意味のない研究だったね」と酷評されて終わってしまうなどという、なんとももったいない話ですが、こんなことも往々に起こっているのではないかと思います。

このパターンが発生する理由は意外とシンプルで、「GPU が最も得意とする処理を、わざわざ余分な苦労を追加して FPGA で無理やり同じことをやっている」からに他ならないケースが多い気がします。そして図らずも 苦労して追加した余計な事 が性能を下げてしまっていることに最後まで気づけないケースです。

そしてこのケースを生み出している要因の一つに、FPGAベンダーが「このツールを使えばGPUでやってるAIをFPGAで開発できるよ」と、GPUの代替になるFPGA を声高に宣伝文句にしている点があるように思います。ベンダーのこのうたい文句は、既にFPGAを使いこなしている人に対して「さらに GPU 市場の AIが簡単に取り込めるよ」という意味も含むので一概に批判もできないのですが、一部の人に誤解を生んでいる可能性はあるように思います。

先日、X で FPGA に USBカメラを繋ぐことについて下記のようなことを書いたら少し反響がありました。

FPGAを カメラのISP(Image Signal Processor) 代わりに使うのが便利だとして使っていたような層には、私と同様に FPGA + USBカメラに違和感を感じる方もおられたようです。

一方で、「GPU の代わりに FPGA を使ってみよう」というところから入ってくる方は、今の Jetson を KV260 に置き換えてみたり、PC で GPUボードが挿さっているところに替わりに Alveo や Agilex を挿さしてみるなどの話になるので、「カメラはそのまま今まで使っていたUSBカメラでいいよね」となってしまい、そこに疑問すら持たないわけです(むしろ条件を揃えて比較しないといけないと思ってわざわざGPUの土俵で比較評価をしてしまうわけです)。

一方で、先に違和感を感じた方からすると「そんなことしたらそれだけでFPGAのいいとこ全部死んじゃうよ!」という悲鳴が上がるのもまたよくわかります。

このやり方で FPGA に入ってきた場合、GPU と同じ条件で GPU に勝たないといけないので、実はかなり大変です。

  • GPUの得意な「同時に同じ計算を大量に」が効かないアルゴリズムで戦う
  • INT7以下とか 独自定義の非線形浮動小数点型とか、GPUにない演算を多用する
  • ホモジニアスなGPUに不利でヘテロジニアスな演算器構造を使うモデルを捻りだして勝ちに行く

などなど、GPUと同じ土俵で戦う際のノウハウと戦略を持っていないと、手も足も出ませんし、これらを駆使しても、常に先端製造プロセスで作られているGPUの地力でねじ伏せられてしまい、とても苦しむことになります。

RECONF研のこちらの天野先生のメッセージリコンフ8策 というのを見かけました。まさに金言だと思います。

ではどういうときにFPGAを使うべきなのか

ここではカメラの例を出しましたので引き続きそのまま例にしますが、FPGAISP として使っている層は、ISP に関しては GPU でやるより FPGA でやる方が、はるかに計算効率が良く、電力もコストもリアルタイム性も勝てることを知っています。

つまり、FPGA がすでに GPU に勝っている領域からスタートし、そこに AI など新しいものを足していく というのが個人的に最もお勧めするやり方です。

画像処理(マシンビジョン)であったり、スマートNICやネットワークスイッチのような通信分野、ロボットなどのリアルタイム制御、特殊なセンサー/アクチュエータなどのデバイス制御、などなど何もしなくても FPGA が圧勝していたり、そもそもCPU/GPUでは不可能なものだったり、FPGAが得意な分野は多数あります。

ここを出発点として、FPGAの強みを失わない範囲で拡張していくことが重要です。

これはズルでも何でもなく、裏返せば GPU も同じことを既にやっていて、自分の得意分野で戦っているから、FPGA より優位に見えているだけです。

計算機科学に触れよう

ここで、多くの場合、GPUはなぜAIが得意で、CPU は何故AI計算でGPUに負けているのか、などの なぜ? に踏み込まず、「FPGAと言うものがあってなんかGPUより高性能らしい」という話だけで、意味も分からず使ってしまうと失敗します。

先のリコンフ8策の分中でも「ハードウェアで実装したんだからソフトウェアに比べて速くなるに決まっている」なんて言葉が飛び出しておりましたが、アカデミック分野に属する先生方からですらこんな声が出る事もあるわけですから、やる側がそのレベルで飛びついてしまってはいけないのです。

もちろん、FPGA は正しく使えば、GPUより高性能になりえますし、わかってくるととても楽しいものです。

ですので、入り口で躓かないために計算機科学に興味を持っていただきたい ということをすごく感じてしまうのです。

ヘネパタ読めとまでは言いませんので、ネット上でいろいろ計算機の仕組みを調べてみたり、実際に CUDAのコードを書いてみて GPU の仕組みに触れてみるとか、いろいろ試してほしいと思います。 そのうえで、自分のやりたいこと、考えているアイデア、拘りたいポイントなどよく考えて、「これFPGAなら試せるアイデアじゃないか?」というゴールまでの道筋をしっかり考えて取り組むことをお勧めする次第です。

新しい時代の FPGA-AI 8策が必要

最後に、今なぜこんなことになっているかを少し振り返っておきます。

私にとって比較的なじみの深い画像信号処理の分野で言えば、アルゴリズムと計算機アーキテクチャをセットで考え、新規性と進歩性のある、新しいシステムを生み出すことが重要です。

ところが、認識率という観点でのみアルゴリズムを研究されている方々の中で、「それはAIと比べてどうなのか?」という ルールベースアルゴリズムの研究の成果の価値がAIと比較されてて、精度観点だけで駆逐されていった と言うのがあります。

また、ビジネスの観点でも、AIにあらずんば投資対象にあらず と言わんばかりに、AIでないと研究予算が取れなくなり、AI人材でないと就職先が絞られていく という事情変化もありました。

必然的に、多くの学生や研究者が何かしら AI と絡めた研究をこぞってやり始めて現状に至ります。

加えて AI の台頭で、GPUを使った GPGPU計算が台頭してきたため、今まで CPUに勝てればOK であったアーキテクチャ研究が、GPU にも勝たなければいけなくなりました。しかもGPUが得意とするAI分野でです。

正直、私はそこまでAIに拘りも無いのですが、時代がそれを許してくれないので、何とか、世の中の需要を満たす建前も必要です。

拙作の LUT-Network などが生まれてきた背景にもそういう部分は無視できません。

時代の変化に合わせて 8策 をアップデートするが必要があるのかもしれません。

GPU と比較されたときの理論武装が必要です。

  • GPU向けのモデルをそのまま使わない(同じ土俵で戦わない)
  • GPUが持つハードマクロ演算器が役立たない演算を入れる(GPUの苦手を狙う)
  • FPGAのLUTやDSPやBRAMの特性を生かしまくるモデルにする(FPGAの得意を活かす)
  • Sparce性、ヘテロ性など、均一でない計算を作る
  • 演算器へのデータ投入でキャッシュより効率の良いメモリアーキテクチャで差をつける
  • リアルタイム性を活かしたアルゴリズムモデルを考える(リカレント構造など)
  • 他の特殊なデバイスと連携する、RGB以外のデータを扱う
  • 複数のセンサーやタイミングを組み合わせる

などなど、様々な要素を考えてみて欲しいと思います。

FPGA はストリーム処理が得意

FPGA は基本的にストリームデータに対するパイプライン処理が得意です。

カメラからのデータはストリーム的に出てきますし、出力もDVIやHDMIなどにストリーム的にそのまま出力できます。

一方で、ストリームデータは一度メモリに貯めれば、GPU などで並列演算可能であり、メモリに格納された GPU の処理結果をまた ストリームに戻すことができます。

この際に

  • メモリに溜めた遅延が増加する
  • メモリと言う新しいコストと電力が発生する
  • メモリとデータ転送を行うDMAなりの新しいコストと電力が発生する

などの不利が発生します。

しかしながら、先に述べた USBカメラの例の場合、

  • USBのプロトコルスタックや V4L などが画像読み出しの段階で、GPUに便利なフレーム単位にメモリに貯めてしまう
  • 結果を表示するにも OpenGL などの為に GPU と同じようにビデオバッファにデータを並べないといけない

という制約の為に、

  • わざわざ GPU用に並列化されたデータをコストを掛けてFPGA用に再ストリーム化する
  • FPGAの出力ストリームをわざわざフレームバッファに貯めなおして、GPUと同じ結果にした後、実は再度、再ストリーム化されて表示される

という非常にもったいないことになっていたわけです。

これで勝とうとすると、よほど「並列に実行したときでもGPUに非効率な計算列」になってない限り勝てず、とても不利な戦いを求められます。

なので、ストリーム入力&ストリーム出力で、リアルタイム性が重要なFPGAの得意な土俵で戦うべきなのです。

リアルタイム性については、「単にサクサク応答すると気持ちい」と言うだけではなく

  • 今の音を逆位相の音で打ち消すノイズキャンセリングのような信号処理
  • 揺れているドローンを安定させる
  • 転ぶ前に足を出してバランスをとるロボット
  • 新しい情報を瞬時に判断して株の売買をするシステム
  • 絶対に負けないジャンケンゲーム

みたいなものを考えていくと、AIを使う事も生きてきますし、FPGAの強みが出てくるわけです。

おわりに

これまで FPGA 人口ってどんどん高齢化していると思っていたのですが、最近 FPGAやってみたいという若手とお話しさせて頂く機会も増えました。大変ありがたいことです。

一方で「FPGA やってみたけど成果が出ない」という相談も増えるようになってきております。

FPGAは苦労も多く手戻りも大きい為、早い段階で 成果の出る道筋 に軌道を向けることが大事です。

同じようなことで悩んでおられる方、「これからFPGAに触ってみたいという方」に、失敗しないFPGAの始め方 を模索する上でのヒントになれば幸いです。