忍者ブログ
  • 2017.09
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 2017.11
SpinLock vs pthread_mutex
スピンロックって知っていますか?
ロック変数を監視してグルグルと回りながら待機するやつですね、はい。

mixiで話題になっていたので、ここでは純粋なスピンロックと
pthread_mutexのパフォーマンスを計測してみました。

スレッドは2つで計測してみました。

タスク量は9900ms(5×108回ループを2回)です。


※CPU負荷はループをひたすらするだけの実行プログラムを
 -Corenのn個分だけ傍で動かしながら計測した結果。

●まずはNoLockから見ていきましょう。
-Core0のDuoの場合、1CPUあたり17%がタスク外、60%の処理時間
-Core1の1CPUの場合、11%がタスク外、112%の処理時間
Core2がきちんと実装されていたことに感動です。私のマイノートPCは速い!!

●pthread_mutexは終わったら終わったよーってsignalで
通知してくれるためなのか(?)、OSのスケジューリングに大きく左右されて
-Core0ではDuoの場合、1CPUあたり、73%がタスク外、190%の処理時間
しかし、すごいのはここからで、
-Core1の場合、25%がタスク外、135%の処理時間
何と負荷がかからない時よりもタスク外が少なくなるのです!!

●SpinLockはその名の通り、サービスとSpinのスレッドの2スレッドになり
仕事量は2倍ですねー。

Core2のマシンでは本来の作業量に近いSpinLockの-Core0とNoLockの-Core1が
ほぼほぼ同じになっています。
-Core0のDuoの場合、1CPUあたり10%がタスク外、112%の処理時間

しかし、残念なことに-Core1にすると、
SpinLockしてたでしょってバレバレなくらい
サービス時間が2倍になってしまっています。
50%がタスク外、202%の処理時間です。

●最後に-Core2についても見てみましょう。
NoLockは17%がタスク外として処理され120%の処理時間
pthred_mutexは30%がタスク外として処理され144%の処理時間
SpinLockは60%がタスク外として処理され250%の処理時間

NoLockは同期を取らないため、1/2タスクに対して約15%の邪魔が入ります。
pthread_mutexは同期を取るので、1タスクに対して約30%の邪魔が入ります。
SpinLockは同期を取り、サービスとSpinの2タスクに対して約60%の邪魔が入ります。

まとめ
SpinLockは余ってるCPUがある前提で使用する。
(Spinという仕事量が増えることを認識しておく)
負荷がある時はpthread_mutexを利用する。
PR
【2012/01/03 13:12 】 | C/C++ | 有り難いご意見(6) | トラックバック(0)
                                    
<<Singleton Shell | ホーム | Cより速いjava (3)>>
有り難いご意見
無題
興味深いですね♪
でっ、テストのソースコードは<(。。

スレッドの負荷モデルがどうなっているのだろうと?

いや深い意味はないすっ(汗)

【2012/01/03 19:30】| URL | ゼンガイチ #2ac02652f5 [ 編集 ]


無題
微妙にmixi内のコピったので^^;
負荷んとこだけ抜粋で♪
s->lock();<ースタートそろえるmutex
s->unlock();
for(i=0; i<5000000; i++)
{
fsl->lock();←計測するmutex or スピンロック
for(j=0;j<100;j++);
fsl->unlock();
}
return NULL;
}

私のソースをmixiのC言語とC++言語の
コミュニティに置いてるので入れたら見てね。
すんません^^;
スピンロックはxchgアセンブラと
変数監視ループのみです。
【2012/01/03 19:50】| | nwpfh #29ef1c77e8 [ 編集 ]


無題
変数監視ループではタイムスライス内に
変数監視が終わった時ようにsched_yieldを
呼んでいます。
【2012/01/03 19:56】| | nwpfh #29ef1c77e8 [ 編集 ]


無題
負荷自体は別の何回もループしてたのを
実行してただけ~。

-Core0では使用せず
-Core1では別のptyから1つ実行
-Core2では別のptyから2つ実行

ですな。
【2012/01/03 20:07】| | nwpfh #29ef1c77e8 [ 編集 ]


無題
ソースコードと解説ありがとうございます♪
なにぶん、mixには入れませんので(汗)

Linuxて標準APIでスピンロックがありませんでしたっけ?

MySQLでは何度も高負荷時にスピンロックで悲鳴をあげますが、大量のクエリーのスレッドを振り分けるのに使っていたような

チョーうろ覚え的ですが、

うーん、うそついてるかもしれないと
いって立ち去りますヾ( ̄ ̄

何を言いたかったのだろう(ぼぞっ)
【2012/01/03 21:27】| URL | ゼンガイチ #2ac02652f5 [ 編集 ]


無題
あはは、にわかスピン調べのため・・

ぶっちゃけ、APIは知らなかったり。。

ソースコードがあったから、測定してみたかったのさ。と言って去ります(笑)

カーネルの本を少し読んで見たくらい。って
あれは低レベルかな。
【2012/01/03 21:37】| | nwpfh #29ef1c77e8 [ 編集 ]


貴重なご意見の投稿














虎カムバック
トラックバックURL

<<前ページ | ホーム | 次ページ>>