見出し画像

ChatRWKVを日本語で試す(Windows11, VRAM 11GB環境)

ローカルで動かすことができ、ソースコードもモデルもApache Licenceで提供されている大規模言語モデルのRWKV。猛烈にアップデートが繰り返されており、なんちゃってChatGPTくらいの性能が出そうな期待感が高まっています。

このRWKVでチャットのようにやりとりできるChatRWKVというプログラムがあります。

さらに、このRWKVのモデルをAlpaca, CodeAlpaca, Guanaco, GPT4AllでファインチューンしたRWKV-4 "Raven"-seriesというモデルのシリーズがあり、この中には日本語が使える物が含まれています。ファイル名に「EngChnJpn」が含まれている以下のファイルです。(14.8GBあるのでディスク容量に注意)

これらを使って、ローカルでChatGPTっぽいものを動かしてみます。私の環境は、Windows11で、使っているGPUはVRAMが11GBのRTX2080Tiです。もう5年近く前のGPUですが、わりと良い感じに動きました。

環境のセットアップ

ここは良い解説があるので、ざっと流します。この部分はたくさんの初心者向けページが世の中にありますので、そちらを参考にしてください。

  • Python 3.10をインストール

  • Windows powershellでgit clone https://github.com/BlinkDL/ChatRWKV.git してChatRWKVのリポジトリをクローン

  • cd ChatRWKVでカレントディレクトリを移動

  • venv環境を作って、venv環境にする

  • pip install ninjaでninjaをインストール

  • pip install rwkvでrwkvをインストール

モデルファイルのコンバート

ダウンロードしたRWKV-4-Raven-7B-v6-EngChnJpn-20230401-ctx4096.pth を、ChatRWKVフォルダに置きます。
14.8GBのファイルは私の環境ではVRAMに収まらないため、コンバートして容量を小さくします。

コンバートは、venv環境になっているChatRWKVフォルダから、powershellで./v2/convert_model.pyを使って以下の様に行います。最後のstrategyオプションで、変換方法を決定しています。

python .\v2\convert_model.py --in .\RWKV-4-Raven-7B-v6-EngChnJpn-20230331-ctx4096.pth --out .\cudafp16i8.pth --strategy 'cuda fp16i8'

--strategyオプションについては、PyPIのrwkvのページに詳細があります。各自の環境に合わせてチューニングすることが推奨されています。私の場合は、全レイヤーをfp16i8にすることで、50%削減をしたというわけです。

########################################################################################################
#
# Use '/' in model path, instead of '\'. Use ctx4096 models if you need long ctx.
#
# fp16 = good for GPU (!!! DOES NOT support CPU !!!)
# fp32 = good for CPU
# bf16 = worse accuracy, supports CPU
# xxxi8 (example: fp16i8, fp32i8) = xxx with int8 quantization to save 50% VRAM/RAM, slower, slightly less accuracy
#
# We consider [ln_out+head] to be an extra layer, so L12-D768 (169M) has "13" layers, L24-D2048 (1.5B) has "25" layers, etc.
# Strategy Examples: (device = cpu/cuda/cuda:0/cuda:1/...)
# 'cpu fp32' = all layers cpu fp32
# 'cuda fp16' = all layers cuda fp16
# 'cuda fp16i8' = all layers cuda fp16 with int8 quantization
# 'cuda fp16i8 *10 -> cpu fp32' = first 10 layers cuda fp16i8, then cpu fp32 (increase 10 for better speed)
# 'cuda:0 fp16 *10 -> cuda:1 fp16 *8 -> cpu fp32' = first 10 layers cuda:0 fp16, then 8 layers cuda:1 fp16, then cpu fp32
#
# Basic Strategy Guide: (fp16i8 works for any GPU)
# 100% VRAM = 'cuda fp16' # all layers cuda fp16
# 98% VRAM = 'cuda fp16i8 *1 -> cuda fp16' # first 1 layer cuda fp16i8, then cuda fp16
# 96% VRAM = 'cuda fp16i8 *2 -> cuda fp16' # first 2 layers cuda fp16i8, then cuda fp16
# 94% VRAM = 'cuda fp16i8 *3 -> cuda fp16' # first 3 layers cuda fp16i8, then cuda fp16
# ...
# 50% VRAM = 'cuda fp16i8' # all layers cuda fp16i8
# 48% VRAM = 'cuda fp16i8 -> cpu fp32 *1' # most layers cuda fp16i8, last 1 layer cpu fp32
# 46% VRAM = 'cuda fp16i8 -> cpu fp32 *2' # most layers cuda fp16i8, last 2 layers cpu fp32
# 44% VRAM = 'cuda fp16i8 -> cpu fp32 *3' # most layers cuda fp16i8, last 3 layers cpu fp32
# ...
# 0% VRAM = 'cpu fp32' # all layers cpu fp32
#
# Use '+' for STREAM mode, which can save VRAM too, and it is sometimes faster
# 'cuda fp16i8 *10+' = first 10 layers cuda fp16i8, then fp16i8 stream the rest to it (increase 10 for better speed)
#
# Extreme STREAM: 3G VRAM is enough to run RWKV 14B (slow. will be faster in future)
# 'cuda fp16i8 *0+ -> cpu fp32 *1' = stream all layers cuda fp16i8, last 1 layer [ln_out+head] cpu fp32
#
# ########################################################################################################

./v2/chat.pyの書き換え

./v2/chat.pyに、strategyやモデルファイルを指定する箇所があるので、そこを書き換えます。

./v2/chat.pyの44~50行目付近で、strategyのオプションをcuda fp16i8にします。

# args.strategy = 'cpu fp32'
args.strategy = 'cuda fp16'
# args.strategy = 'cuda:0 fp16 -> cuda:1 fp16'
# args.strategy = 'cuda fp16i8 *10 -> cuda fp16'
# args.strategy = 'cuda fp16i8'
# args.strategy = 'cuda fp16i8 -> cpu fp32 *10'
# args.strategy = 'cuda fp16i8 *10+'

↓ 変更

# args.strategy = 'cpu fp32'
# args.strategy = 'cuda fp16'
# args.strategy = 'cuda:0 fp16 -> cuda:1 fp16'
# args.strategy = 'cuda fp16i8 *10 -> cuda fp16'
args.strategy = 'cuda fp16i8'
# args.strategy = 'cuda fp16i8 -> cpu fp32 *10'
# args.strategy = 'cuda fp16i8 *10+'

./v2/chat.pyの61行目付近で、読み込むモデルを先ほど変換したモデルにします。

# Use convert_model.py to convert a model for a strategy, for faster loading & saves CPU RAM 
if CHAT_LANG == 'English':
    args.MODEL_NAME = '/fsx/BlinkDL/HF-MODEL/rwkv-4-raven/RWKV-4-Raven-14B-v6-Eng-20230401-ctx4096' # try +i for "Alpaca instruct"
    # args.MODEL_NAME = '/fsx/BlinkDL/HF-MODEL/rwkv-4-raven/RWKV-4-Raven-7B-v6-Eng-20230401-ctx4096' # try +i for "Alpaca instruct"

↓ 変更

# Use convert_model.py to convert a model for a strategy, for faster loading & saves CPU RAM 
if CHAT_LANG == 'English':
    args.MODEL_NAME = './cudafp16i8.pth' # try +i for "Alpaca instruct"
    # args.MODEL_NAME = '/fsx/BlinkDL/HF-MODEL/rwkv-4-raven/RWKV-4-Raven-7B-v6-Eng-20230401-ctx4096' # try +i for "Alpaca instruct"

変更したらちゃんとセーブしておきましょう。あとはPowerShellで以下の様に起動すれば、PowerShell上でチャット出来るようになるはずです。

python .\v2\chat.py

実際にやりとりしてみると、ChatGPTほどは賢くありませんが、なかなか饒舌で楽しいヤツなので可愛く見えてくると思います(笑)

Bob: こんにちはアリス。あなたの自己紹介をしてください
Alice: こんにちは、アリスです。私はアリスといいます。私は常に興味深いことに挑戦しています。私の趣味は、簡単な物事を続け
ることです。常に変化していくような素晴らしい経験をしている人にとって、楽しくて少ない時間を充実させるためにもっとお金をかけたほうがよいのではないでしょうか。

人間側がBob、RWKVによる回答がAliceです

Bob: 少年漫画の主人公の必殺技を5個考えてください
Alice: 少年漫画の主人公の必殺技を5個考えてください。
1. 必殺技: "ピアノの奏でるサウンド" - 青春を駆ける一心で奏でる必殺技であり、何度も振り返っても新鮮な感じがする。
2. "ピアノの弾き語り" - 時に独特な雰囲気を持ったまま、サウンドを上手に伝えられる必殺技であり、自然なテンポで語りかけることもできる。
3. "ロケットスクランブル" - 高揚感を持たせたスクランブルストレートが上手く活用できる必殺技である。
4. "ジャンプ爆弾" - 熱い味わいを溢れた爆弾スクランブルの上から飛び立つ一撃のジャンプ爆弾。
5. "アヒルがおとわになるフォーム" - いつものエクササイズと違って、少年漫画的なアクションを楽しむためのオリジナル技術である。
6. "ジャンプキック" - 少年漫画のキャラクターが体を使った腕立て伏せと、相撲や柔道の中間に位置するジャンプキックはおもしろい技法です。
7. "雨漏れ伝わる爆音" - 小さな動きから大きな音を発し、単純かつ耐久性を持ち、衝撃に耐えられる身体能力を持つ少年漫画の伝わる味わい。
8. "エクササイズ的な暴力行動" - 相手に無防備になりつつ突進したり、素早く身体を動かしたりする動きであらゆる雰囲気を引き出すことができる。
9. "アクションシューティング" - 小さな冒険者である少年漫画の中でも極めてアクション的な味わいのシーンができる。
10. "イマジネーション抜きのエッセイ" - 少年漫画は人間関係や価値観などを描き出すことが多くあり、それらの事実関係に基づい
て「イマジネーション味」と呼ばれるエッセイが書かれています。これは難解であるというよりは適切だと思います。

あなたは小学生か高校生ですか?あなたのイメージはどちらですか?尊敬している人物:医者
お勧め漫画:片渕須直
最近買った物:タトゥー好きの人物
最近友達には喜ぶか分からない事になってると思う
好きだけど、友達には喜ばない事になっていてもまだ良いと思う
今月末に会う予定だったしね!(笑)
本当に運が良かったよ
最後にお勧めする物は?
お勧め物ではないです!あまり推奨しないですね!
最後にお勧めする物は?

全て言えないから答えられない(笑)


今月末に会う予定だよ

最後に

人間側がBob、RWKVによる回答がAliceです

必殺技を5個考えてと言ったのに10個考えたばかりかオススメの漫画や自分の好きな物を語り始めるあたり、早口オタク感があっていいです。ちなみに、Pythonのコードなども考えてくれます。かなり使えそうです。

RWKVはファインチューニングもできるようなので、自分好みに作り替えていくこともできそうです。オープンなモデルをローカルで動かす事の良さは、外国の会社が設定した基準に縛られないことだと思うので、自由な発想が必要になる場面ではとくに有り難い存在になるのでは、と思っています。

引き続き、オープンなモデルをローカルで動かすことに注目していきたいと思います。

追記

上記は7B(70億パラメーター)モデルを動かしたものですが、14B(140億パラメーター)も、convert_model.pyを以下の様にすることで、VRAM 11GB環境で動きました。

python .\v2\convert_model.py --in .\RWKV-4-Raven-14B-v6-EngChnJpn-20230401-ctx4096.pth --out ./14bfp16i8_25_cpufp32.pth --strategy 'cuda fp16i8 *25 -> cpu fp32'

モデルの25レイヤー分をCUDAに、残りをCPUに逃がすという設定です。

PowerShellに表示されたレイヤーに関する情報

./v2/chat.py も、以下の様になります。

args.strategy = 'cuda fp16i8 *25 -> cpu fp32'

(中略)

 args.MODEL_NAME = './v2/14bfp16i8_25_cpufp32.pth'

ただ、結局CPUのメモリを経由するので、遅いです。実用的な速度ではありませんでした。24GBや48GBのVRAM搭載のビデオカードを買えば14Bでもストレスなく動くかも?


この記事が気に入ったらサポートをしてみませんか?