Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

previewのonnx版コアを使った合成で、開始・終了無音を0.3~0.4秒くらいにすると音声が変になることがある #62

Closed
Hiroshiba opened this issue Jan 6, 2022 · 9 comments

Comments

@Hiroshiba
Copy link
Member

不具合の内容

エディタのプレビュー版をインストールすると、onnx版のコアを使った生成ができます。
https://github.com/VOICEVOX/voicevox/releases/tag/0.10.preview.4
生成が速くて魅力的なのですが、音声の品質が以前より悪いことが何度かあり、ちょっと気になっています。

例えばですが、「どれもこれも反省しているのだ」と入力し、開始無音を0.4秒に再生すると、最初の「ど」の音がちょっと潰れてしまいます。

voicevox-cpu.2022-01-07.06-33-14.mp4

現象・ログ

前後の無音時間を0.3~0.4秒くらいにすると、音が変になることがある。

再現手順

エディタのバージョン0.10.preview.4にて、あまあまずんだもんで「どれもこれも反省しているのだ」を、開始無音を0.3秒くらいにして再生する

期待動作

以前と同じ音声が再生できる。

その他

差が出ているのがonnx化したからなのか、間違えて違うモデルを利用しているからなのかがわかりません。
ただ、記録を確認した感じ以前と機械学習済みモデルが同じはずなので、同じ結果が返るはずなんだよなぁと感じています。
(実際音素長と音高は完璧に同じ値が出力されています。)

結構微妙な差ではありますが、こういう微妙な品質ダウンがユーザー心情を悪くするのかなと思ったので、真剣に原因を探りたいなと思いました。

libtorch版とonnx版で、decode_forwarderの出力結果って完全に一致するかをちょっと確認したいかもです。 @Yosshi999
無音時間が特定の長さになるとエラーになるのは、onnx化するときに変換が若干不完全な部分があって、例えばconvolutionの受容野の範囲の関係で偶然そうなっているのかなぁなどと考えています。

ref

@Hiroshiba Hiroshiba changed the title previewのonnx版コアを使った合成で、開始・終了無音を0.3~0.4秒くらいにすると音声が壊れることがある previewのonnx版コアを使った合成で、開始・終了無音を0.3~0.4秒くらいにすると音声が変になることがある Jan 6, 2022
@Yosshi999
Copy link
Contributor

float計算の再現性はなかなか難しくて、特にdecodeについてはonnx化をやった当時は結局諦めてしまいました( Hiroshiba/vv_core_inference#1 (comment) )。
なので出力を比較すれば恐らくずれていますが、本質的に何かが壊れているのか、float演算の誤差なのかは何とも言えません。ネットワークを分割して中間出力とにらめっこするしかなさそう?

あやしそうな点としては自作のpositional encodingを差し込んでいるところ(https://github.com/Hiroshiba/vv_core_inference/blob/539ca8f90de038471d22857ffdff496db2788009/vv_core_inference/make_yukarin_sosoa_forwarder.py#L141 )ですが、ここがおかしければ音声がもっと破綻してそうな気もします。

@Hiroshiba
Copy link
Member Author

あーーーなるほどです > positional encoding
おっしゃる通り、僕も中間層の出力をひとつずつ確認とかになるのかなと感じてました。

(あとはなんとなくですが、weight norm辺りが意外とバグってるのかもなぁとちょっと思いました。挙動がなんかnormalize周りっぽみ感じたので)

@Yosshi999
Copy link
Contributor

weight normは確かonnx変換前に解除しないと失敗しますね

@Hiroshiba
Copy link
Member Author

改めていろいろ試してみたところ、どうやら無声化された音素周りも苦手になっている印象でした。
F0の値が0で入力されている周りに何か問題があるのかもしれません。

こちら、わりと顕著に悪くなってしまっているので、バージョンアップまでに修正したいと考えています。
自分が取り組むつもりだったのですが、今回はバージョンアップ内容がてんこ盛りで、広範囲の調整に時間がかかってしまっています。

この分野は専門知識が必要で、修正できる方はとても限られている状況で、@Yosshi999 さんの力をぜひお借りしたいのですが、どうでしょう・・・?👀

@Yosshi999
Copy link
Contributor

一応ちょっと調べなおしてみたんですが、https://github.com/Hiroshiba/vv_core_inference/blob/539ca8f90de038471d22857ffdff496db2788009/vv_core_inference/make_yukarin_sosoa_forwarder.py#L126 ですでにtorchとonnxで誤差が発生しています。おそらく計算順序によるものだと思いますが、これが今回の異常と関係があるかは分かりません

これ以上深く調べるには秘匿情報が多すぎてちょっと厳しいですね。そもそも現状ではvv_core_inferenceレベルで異常が起こっているかどうかもよくわかってなくて、engineレベルのバグである可能性も残っていますよね?

@Hiroshiba
Copy link
Member Author

おお、なるほどです!!
preの出力箇所で、ということでしょうか👀

たしかに、推論の段階ではなくエンジンの段階である可能性も全然ありそうです。
ちょっと推論部分だけ変えて生成結果を比較してみます…!

@Hiroshiba
Copy link
Member Author

生成してみようとしていろいろしてたところ、原因がわかりました。

https://github.com/Hiroshiba/vv_core_inference/blob/539ca8f90de038471d22857ffdff496db2788009/run.py#L61-L66

どうやら↑の部分で、話者数分だけ何度もconvertしているためっぽかったです。
1回だけconvertにすれば品質の差はほとんどなくなりました。
たぶん1回convertするたびに誤差が増えて、何度も変換することで蓄積していくのかなと推察しています。

@Hiroshiba
Copy link
Member Author

とりあえず変更を1度だけにするようにしたいと思います。
もし可能であれば、onnx化の段階で品質を全く変わらなくできるととても嬉しいです・・・!

@Hiroshiba
Copy link
Member Author

出力が変わることに関してはこちらのissueで続けたいと思います。

主問題は解決したのでcloseします!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants