Perfmon 執行緒數與 SQL 工作者
我們正在嘗試監控 SQL 工作執行緒,過去我們使用以下查詢:
選擇總和(current_workers_count)作為
$$ Current worker thread $$FROM sys.dm_os_schedulers 我們現在正在考慮只為每個 SQL Server 實例使用 PerfMon 計數器“Process>Thread Count”。在我們的分析過程中,我們注意到 PerfMon 執行緒計數與 dm_os_scheduler 或 dm_os_workers 中的工作執行緒之間存在細微差別。我們還將它與 dm_os_threads 中的內容進行了比較,仍然發現了差異。有誰知道 Microsoft 提供的 DMV 中跟踪的內容與 PerfMon 擷取的內容之間的區別?DMV 始終低於性能監視器中的值,因此它們必須“排除”某些東西。我們需要了解那是什麼。
例如,dm_os_threads dmv 將顯示 137,但性能計數器將顯示 141,dm_os_scheduler 和 dm_os_workerss dmv 將分別顯示 122 和 123。
我們使用的是 SQL Server 2017,CU22;視窗伺服器 2016
我最初關於執行緒使用的討論可以在這個答案中閱讀。
但是為什麼 dm_os_threads 的結果與 PerfMon 的結果不同呢?
執行緒 DMV 只會公開 SQL Server 知道的執行緒,因此它只會有它引導的執行緒。本質上,您只會看到 SQL Server 直接或間接啟動並將某些資料結構掛鉤到 TLS 的執行緒。
一個簡單的例子是,假設我有一個 3rd 方防病毒應用程序,我們稱之為“Sarbon Yack”或簡稱 SY。SY 可能會自行將自己的模組載入到 SQL Server 記憶體空間中——這是不受支持的。當這些模組被載入時,它們可能會啟動許多不同的執行緒——但是通過引擎啟動它們的不是 SQL Server,實際上是一個外部模組啟動了它們。從技術上講,它們存在於流程的範圍內並被報告,但 SQL Server 不知道它們的存在,並且它們沒有附加任何 SQL Server 資料結構。這些執行緒不會出現在 DMV 中。
PerfMon 包括哪些未包含在 DMV 中的內容?
我不知道 perfmon 的程式碼,但 perfmon 不會創建值,它只是在要求返回值時從不同的數據源讀取(例如通過添加計數器)。我的直覺告訴我,當在程序空間中創建執行緒時,內部值會增加,而當執行緒被任何跟踪它的程式碼破壞時,內部值會被刪除。
該值本身不知道 SQL Server 是什麼或它如何使用執行緒,它只是查看一個抽象的“程序”(這是您將在每個程序下找到執行緒值的內容)並讀取有關數字的資訊執行緒,然後返回該值。它不區分什麼是 SQL 增強執行緒和什麼不是。
我最好的猜測可能是通過呼叫NtQuerySystemInformation for SystemInformation 來返回System_Process_Information結構的列表,該結構將保存程序中的執行緒數。我最好的猜測是(執行緒數)是通過遍歷 _EPROCESS 資料結構中的執行緒列表來合併存在的——但在核心或使用者模式結構中的某處也可能有一個針對這個特定事物的計數器,而我只是不這樣做’看不到它或知道它的存在。
_EPROCESS 中的執行緒列表:
+0x470 ThreadListHead : _LIST_ENTRY