-
Notifications
You must be signed in to change notification settings - Fork 6
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
LogPosition::is_newer_or_equal_than の定義ミスによって生じる無限ループについて #46
Comments
詳細にありがとうございます。 実装当時の詳細はうろ覚えなので、適切なことを即答はできないのですが「期待される定義」に記載されている以下の定義に単純に書き換えてしまって大丈夫なのかどうかは、若干気になっています。
理由としては、Raftのアルゴリズム的にtermはいろいろな理由で大きな値になることがあり、その場合にtermだけみて次のリーダを決めてしまうと、不整合が発生するのではないかと思いました。 ちょっと、issueの内容を完全に把握している訳ではないのと、Raftの論文もうろ覚えなので、時間がある時にでも再確認してみます 🙇 |
コメントありがとうございます。 Ohtaさんのコメントは至極真っ当で、明らかにしておかなければならない点だと思います。 まず、定義中の
の
というところが注意を要する点だと思います。 いま急いで付け足さなければならないのは次の点です(具体例は以降で見ます):
これは、Ohtaさんが気にしている(であろう)
といった状況が辞書式順序でも起こらないということを保証しています。 上記「currentTermだけが大きいnodeはleaderになれない」を確認するために、次のようなconfigurationを考えたいです:
話を簡単にするために、Index 99がcommittedだとします。 これは
という状況を反映しています。 さて、この状態で B がネットワークに復帰して、VoteCallをbroadcastする場合を考えます。
結局のところ
ということになります。 参考になっていれば幸いです。 |
ありがとうございます。後でまたちゃんと確認させて貰います 🙇 |
スパッと納得に通じるとそれに越したことはないのですが、そうでない場合は |
この件、全く確認できていないですが、十月には少し時間ができる予定なので、そこで対応しようと思っています(既に一ヶ月放置してしまっていますが、一応情報共有)。 |
ありがとうございます。 現状のコードだと極端な場合に困るので、論文の順序の定義を採用したいという話なのですが、
あたりだと思うのですが、他になにかありそうでしょうか。 |
上記以外で気になる点は特にないですね。 |
どれだけ頷いても頷き足りないほど同意です。 ひとまず上のdescriptionは 一方でより深いレベルの話については…… これは相当難しいと思っています。 |
だいぶ遅くなってしまいましたが、改めてissue/実装/論文を確認させて貰いました。 結論から言えば「@yuezatoさんが提案されている内容に修正して問題なさそう(というかそちらの方が確かに論文通りになっていて良さそう)」ということになります。 最初にコメントを書いていた時に、↓の点を失念していたのが混乱の原因でした...。
詳細な説明をありがとうございました 🙏 |
Leaderがいつまで経っても決まらずに、無限ループとなりサービス不能となるバグがあるのでそれについて述べる。
is_newer_or_equal_than
とは?中身(定義)は次節で述べるとして、どこで使われていて、直感的な意味は何かをまず述べる。
Common::handle_message
raftlog/src/node_state/common/mod.rs
Lines 300 to 304 in 05c3d32
が(テストコードを除くと)唯一使用されている箇所である。特に次の箇所である:
raftlog/src/node_state/common/mod.rs
Lines 325 to 330 in 05c3d32
これは raft論文 https://raft.github.io/raft.pdf の Figure2
RequestVote RPC
のに対応しているだろう。ここで
up-to-date
というのは論文の5.4.1節で定義されている全順序である。詳しくは下の方で述べる。一言で言うなれば、
is_newer_or_equal_than
は leader node を決定する上で鍵となる述語である。これは、上で抜粋したコードで行っている計算からも明らかである(下は無理やり日本語にしたもの):
現在の定義
現在のraftlogでは、
LogPosition
上の順序is_newer_or_equal_than
が以下のように定義されている:raftlog/src/log/mod.rs
Lines 272 to 274 in 05c3d32
Note:
LogPosition
は term と index の組:raftlog/src/log/mod.rs
Lines 233 to 241 in 05c3d32
現在の順序は、
(termL, indexL) ≽ (termR, indexR)
が成立するのは直積順序が成立する時、すなわちを要求している。
期待される定義
is_newer_or_equal_than
は、raft論文 https://raft.github.io/raft.pdf の 5.4.1 節 の最後にあるパラグラフ:に対応していると考えられる。このパラグラフが要求しているのは辞書式順序
2つの定義の違いと、それによる問題点
全順序でない順序をLeaderの裁定基準に採用する場合には、優劣を決定できないために計算が次のステージ/Termに持ち越され、次のステージ/Termでも結局判断出来ず、これが繰り返されいつまでも決定できないということが起きうる。
実際に、無限ループとなりLeaderがいつまでも決定できずクラスタが使用不能になる例について
上里の再現用ブランチを確認されたい。
修正方法 と 気になる点
修正方法については、論文の定義に直すだけで良い。
一方で、全順序とならないことを承知の上で、現在の定義を採用した可能性がある:
raftlog/src/log/mod.rs
Lines 265 to 266 in 05c3d32
USENIXに公開されているバージョン https://www.usenix.org/node/184041. から
up-to-date
の定義は変わらず辞書式順序のままなので、辞書式順序版になにかミスがあることを見越して異なる定義を採用した可能性がある。
あるが、この辞書式順序はRaftアルゴリズムの根幹を支える直観と密接に関係していることと、
多少粘った程度では「辞書式順序で問題がある=論文の安全性をひっくり返す」ようなことは示せていないので、
論文の定義に戻したい。
The text was updated successfully, but these errors were encountered: