##そういえば『プログラミング Gauche』にたしか協調的マルチスレッドのサンプルがあったような。
#「19.8 コルーチン」これかしら
#今のGaucheだと、shift/resetがあるから、そっちを使った方が軽いのかな←よくわかっていない
#あー、部分継続ですか。使った事ないですが、たしかにそっちの方があってそう。Lua のコードも上の Gist に足してみましたが、組み込みのコルーチンを使うのでほとんど何もしないコードになっちゃいました。
##そうそう。それ壊れてるみたいです。ただ、答えは簡単で、整数の引数と一つとって、答えはかならず N % 503 + 1 です。N は 50,000,000 で計測するみたい。
#tokenは何でもいいの?
#特に指定はないように思うんですが。
#要はスレッド切り替えのパフォーマンスを計測する、という話なんだろうか(←まだよくわかっていない)
#スレッドからスレッドにどれだけ早くバトンを渡していくか、という話のように読める。
#そうそう。 http://d.hatena.ne.jp/kazu-yamamoto/20110902/1314934306 ここからたどりました。Haskell は Erlang より速いぜって書いてあるので、じゃあ Lua や Scheme でもやってみようかなとおもって。 #なるほど。協調型マルチスレッドやコルーチンの場合は「interesting alternative」扱いってことですよね。
#プリエンプティブなユーザスレッドを実現するためには、処理に割り込んで別のスレッドにyieldさせるしくみ(つまりスケジューラ)が必要って理解で正しいのかな。
#このあたり、普段は漫然と使ってるだけであまり深く考えてないから、弱いなー。
#ああなるほど。
#Earlangのユーザスレッド(プロセス)はプリエンプティブだとは知っていたけど、それと退避するくらいなんだから、GHCのユーザスレッドもプリエンプティブなんだろうな。
#s/退避/対比/
#確かにスレッド切り替えにはコンテキストの退避が書かせませんが ;-)
#s/書かせ/欠かせ/
#日本語ボロボロだ
#あー、じゃあ Lua で勝負するのはあんまりフェアじゃないのかな。
#フェアとかじゃなくて、土俵がちょっと違うってことじゃないかなぁ
#プリエンプティブなスレッドのスレッド切り替えがどのくらい速い/遅いor軽い/重いって話に読めるので。
#これ、別に次の番号を持つスレッドにトークンを渡せとは一言も書いてないなぁ。だとしたら、スレッドプールに投げ込んで後はよろしく、でもOKなのかしらん。そうすると、最後に帰ってくる値が決定しないからだめか。
#どれでもいいから起きてくれ、というのと、特定のスレッドを起こす、というのとでは要求されるものがちょっと違うよなぁ。
##最初にリンクリストをつくってるから、リンクしてないスレッドにはトークンを渡せないということじゃないですかね。
#pre-emption と scheduler は別の話ではないかと思います.scheduler が必要,というのはその通りですが.
#ん、それは、pre-emptionの実現にとって、schedulerは必要条件だが十分条件ではない、という理解でOK?
#ああそうか、割り込み機構+スケジューラか。俺、割り込みかけるのもスケジューラの仕事だと思ってた。
##馬鹿正直にネイティブスレッドとmutexを使って実装してみたんだが... これがうまく動かない。なんでやろ??
#何か絶対しくじってると思うのだけど、よくわからないのでそのままさらしときます。
#あれ、でもFreeBSD 8.2Rだとちゃんと503 50000000でも完了するな。Mac OS Xだと止まっちゃうんだけど。
#デッドロック?
#どうなんだろう
#止まった状態で(この実験の時はthread-ring-start!の最後のthread-join!をコメントアウトしてreplで実行)、(dump-thread-ring-state ring)すると、1個mutexがunlock/not-abondaned になってる
#帰ってから考えよ
#一応、pthread_mutexattr_init(3) には PTHREAD_MUTEX_NORMAL mutexes will deadlock if reentered, and result in undefined behavior if a locked mutex is unlocked by another thread. って書いてあります
#なるほど
#今回引っかかるのは後段かなぁ。
#ロックした人がアンロックするのが基本なわけね
#そういえばそんな話を聞いた気もする。我ながらひどいな...
#あれ、でもSchemeレベルのmutex-lock!/mutex-unlock!はレイヤが違うけどどうなんだろう (mutex-lock! は状態のチェック時だけpthread mutexをロックして、既にSchemeレベルでロックされてたらpthread_cond_waitするんでそこでpthread mutexのロックは外れる)
#FreeBSDで振る舞いが違うから、何らかのOS依存なものが関わってるんだろうけど。
#なるほど。ということは、一つ unlock な mutex があるということは動くべき thread が動いてないのかな。
#そうですね。awakeされるはずのスレッドが起きてないような感じ
#% gosh gistfile1.scm 503 3
zsh: bus error gosh gistfile1.scm 503 3
#バスエラーがでちゃいます。Gauche 0.9.2 Snow Leopard。