自旋(spin)是一種經過不間斷地測試來查看一個資源是否變爲可用狀態的等待操做,用於僅須要等待很短的時間等待所需資源的場景。使用自旋這種「空閒循環(busy-loop)」來完成資源等待的方式要比經過上下文切換使線程轉入睡眠狀態的方式要高效得多。但若是自旋了一個很短的時間後其依然沒法獲取資源,則仍然會轉入前述第二種資源等待方式。html
innodb_sync_spin_loops參數是自旋鎖的輪轉數,能夠經過show engine innodb status來查看。相較於系統等待,自旋鎖是低成本的等待;不過它是一個活躍的等待,會浪費一些cpu資源。所以若是看到大量的自旋等待和自旋輪轉,則很顯然它浪費了不少cpu資源。浪費cpu時間和無謂的上下文切換之間能夠經過該值來平衡。mysql
innodb_spin_wait_delay算法
Vadim Tkachenko 在http://www.mysqlperformanceblog.com/2011/12/02/kernel_mutex-problem-or-double-throughput-with-single-variable/中對該參數進行了測試,並給出告終論。sql
Peter Zaitsev在http://www.mysqlperformanceblog.com/2011/07/28/how-innodb-contention-may-manifest-itself/中也進行了解釋在不一樣情況下,該值的影響。並在http://www.mysqlperformanceblog.com/2006/07/17/show-innodb-status-walk-through/中詳細解釋了show innodb status的輸出進行了詳細解釋。服務器
innodb_thread_concurrency併發
http://dev.mysql.com/doc/refman/5.5/en/innodb-parameters.html#sysvar_innodb_thread_concurrencyapp
Command-Line Format --innodb_thread_concurrency=# Option-File Format innodb_thread_concurrency Option Sets Variable Yes, innodb_thread_concurrency Variable Name innodb_thread_concurrency Variable Scope Global Dynamic Variable Yes Permitted Values Type numeric Default 0 Range 0 .. 1000
InnoDB tries to keep the number of operating system threads concurrently inside InnoDB less than or equal to the limit given by this variable. Once the number of threads reaches this limit, additional threads are placed into a wait state within a FIFO queue for execution. Threads waiting for locks are not counted in the number of concurrently executing threads.less
The correct value for this variable is dependent on environment and workload. Try a range of different values to determine what value works for your applications. A recommended value is 2 times the number of CPUs plus the number of disks.ide
The range of this variable is 0 to 1000. A value of 0 (the default) is interpreted as infinite concurrency (no concurrency checking). Disabling thread concurrency checking enables InnoDB to create as many threads as it needs.函數
參數的含義是: InnoDB內部的併發線程數.
能夠動態修改
具體解析: InnoDB 試圖保持InnoDB內部的併發操做系統的線程數少於innodb_thread_concurrency設置的值
若是innodb併發線程數快要到達innodb_thread_concurrency=x,其餘的innodb線程會被設置爲等待狀態,隊列的算法是FIFO
處於等待拿鎖狀態的線程數,不會被計算入正在執行的併發線程數
innodb_thread_concurrency=x,x該設怎樣的值,視服務器配置和服務器的負載狀況。
默認推薦的值是 (cpu的數量+磁盤數量)x2 (個人理解,對於raid10的磁盤陣列,應該是磁盤總數/2)
參數取值範圍 0-1000 當爲默認值的時候,不是說0個併發線程。 而是被解釋爲無限併發(沒有併發檢查)
當innodb_thread_concurrency=0的時候,能夠理解爲 禁用線程併發檢查,使InnoDB按照請求的需求, 創造儘量多的線程.
http://www.dbathink.com/2012/10/trouble-shooting-the-high-sys-cpu-in-mysql-server/
併發控制
併發控制點:
sql的執行牽涉到server層和引擎層:
因此在MySQL實例中,有兩個最佳的併發控制點:
併發控制大小:
經驗值:# Try number of CPU's*2 for thread_concurrency
但還須要配合具體的平臺和業務系統進行測試,才能找到最佳值。
Innodb併發控制
Innodb使用參數innodb_thread_concurrency控制併發線程的個數,源碼中使用一對函數:
Innodb實現語句級的併發控制,在語句執行結束,stmt commit的時候,強制釋放資源。
權衡和優化
Innodb引入了n_tickets_to_enter_innodb參數,sql進入innodb執行時進行初始化,默認值500。
在執行過程當中,依次進行遞減,遞減到0時,強制退出併發線程,從新搶佔。
好處: