禁用超线程可以提高SQL Server安装的性能

关于: 目前在SQL Server和超线程上的智慧

最近,我们将Windows 2008 R2数据库服务器从X5470升级到了X5560 。 理论上两个CPU都有非常相似的性能,如果有的话X5560稍微快一些。

但是,SQL Server 2008 R2在过去一天左右的performance一直不错,CPU使用率也相当高。

页面预期寿命很长,我们正在为页面获得几乎100%的caching命中,所以内存不是问题。

当我跑时:

SELECT * FROM sys.dm_os_wait_stats order by signal_wait_time_ms desc 

我有:

 wait_type waiting_tasks_count wait_time_ms max_wait_time_ms signal_wait_time_ms
 -------------------------------------------------- ---------- -------------------- -------------------- -------------------- --------------------
 XE_TIMER_EVENT 115166 2799125790 30165 2799125065
 REQUEST_FOR_DEADLOCK_SEARCH 559393 2799053973 5180 2799053973
 SOS_SCHEDULER_YIELD 152289883 189948844 960 189756877
 CXPACKET 234638389 2383701040 141334 118796827
 SLEEP_TASK 170743505 1525669557 1406 76485386
 LATCH_EX 97301008 810738519 1107 55093884
 LOGMGR_QUEUE 16525384 2798527632 20751319 4083713
 WRITELOG 16850119 18328365 1193 2367880
 PAGELATCH_EX 13254618 8524515 11263 1670113
 ASYNC_NETWORK_IO 23954146 6981220 7110 1475699

 (10行受影响)

我也跑了

 -- Isolate top waits for server instance since last restart or statistics clear WITH Waits AS ( SELECT wait_type, wait_time_ms / 1000. AS [wait_time_s], 100. * wait_time_ms / SUM(wait_time_ms) OVER() AS [pct], ROW_NUMBER() OVER(ORDER BY wait_time_ms DESC) AS [rn] FROM sys.dm_os_wait_stats WHERE wait_type NOT IN ('CLR_SEMAPHORE','LAZYWRITER_SLEEP','RESOURCE_QUEUE', 'SLEEP_TASK','SLEEP_SYSTEMTASK','SQLTRACE_BUFFER_FLUSH','WAITFOR','LOGMGR_QUEUE', 'CHECKPOINT_QUEUE','REQUEST_FOR_DEADLOCK_SEARCH','XE_TIMER_EVENT','BROKER_TO_FLUSH', 'BROKER_TASK_STOP','CLR_MANUAL_EVENT','CLR_AUTO_EVENT','DISPATCHER_QUEUE_SEMAPHORE', 'FT_IFTS_SCHEDULER_IDLE_WAIT','XE_DISPATCHER_WAIT', 'XE_DISPATCHER_JOIN')) SELECT W1.wait_type, CAST(W1.wait_time_s AS DECIMAL(12, 2)) AS wait_time_s, CAST(W1.pct AS DECIMAL(12, 2)) AS pct, CAST(SUM(W2.pct) AS DECIMAL(12, 2)) AS running_pct FROM Waits AS W1 INNER JOIN Waits AS W2 ON W2.rn <= W1.rn GROUP BY W1.rn, W1.wait_type, W1.wait_time_s, W1.pct HAVING SUM(W2.pct) - W1.pct < 95; -- percentage threshold 

得到了

 wait_type wait_time_s pct running_pct
 CXPACKET 554821.66 65.82 65.82
 LATCH_EX 184123.16 21.84 87.66
 SOS_SCHEDULER_YIELD 37541.17 4.45 92.11
 PAGEIOLATCH_SH 19018.53 2.26 94.37
 FT_IFTSHC_MUTEX 14306.05 1.70 96.07

这显示了大量的时间同步查询涉及并行(高CXPACKET)。 另外,有趣的是,许多这些问题查询正在多核上执行(我们的代码中没有任何地方提供MAXDOP提示)

服务器已经超过一天左右没有负载。 我们在执行查询时遇到了很大的差异,通常很多查询看起来比我们以前的数据库服务器慢,而且CPU真的很高。

将禁用超线程有助于减less我们的CPU使用率和增加吞吐量?

我仍然认为按照原始答案来testing你的具体工作量是唯一可以确定的方法。 当你试图调整一个生产系统的时候,这不是一个理想的答案(所以我会问是否可以在性能和可用性真正重要的系统中获得一个完全相同的testing平台),但这是我唯一真正感到舒服的用。

我们可以谈论超线程是否应该伤害或改善一般情况的理论(我发现它更可能伤害,而不是服务器上的帮助,所以对于“通用”部署,我可能会禁用它),但是只有一种方法可以确定它是否会影响你的具体情况,那就试试看吧。

我同意

  • 最好的build议是“在你的工作量上尝试超线程,看看会发生什么”。 我现在正在打字,而且这样不好!
  • 你应该总是先禁用HyperThreading,因为这是最安全的

看起来我们应该调整两件事情:

  1. MAXDOP(最大并行度)。 我读过的每一样东西都表明,无界限可能是一个坏主意, 微软的文档说:

    将此选项[MAXDOP]设置为[8以上]的值通常会导致不必要的资源消耗和性能下降。

    一般不build议高于8东西,所以我现在把它设置为4 。 最初是零(无界)。

  2. 并行性的成本阈值。 显然这里默认的5被认为是一个相当低的默认值,根据我发现的一些SQL MVPpost – 我们可以调整它,以减less调度程序甚至尝试了多less平行度。

但老实说,这些都是解决方法。 我认为我们工作负载的真正解决scheme(全文索引大)是禁用HT。

Anandtech发现,随着纯读取负载,它受到一点伤害,并写了沉重的负载,这是一个胜利。 我还没有看到任何让我觉得这会让你的命中率低于-5%,或者比15%的胜率更胜一筹。 注意Atom是什么,这是一个巨大的胜利,但这是一个非常奇怪的CPU。

你改变的是CPU? 你从12MBcaching和4个线程,每个线程caching3MB到8MBcaching,以及8个线程,每个线程1MB。 现在,这只是过度简化,但我敢打赌,是什么杀了你,你曾经在caching中运行查询,现在从RAM运行它们,因为他们需要超过1MB,但不到3MB。 closuresHT可能会有帮助,但我会回到旧的CPU。 关掉HT,每个线程得到2MB,但是如果你的工作量太大,就没用了。 很可能,旧的12MBcachingcpu对于您的工作负载而言要快得多。

我会尝试closuresHT,看看这是否是一个改进,但我怀疑caching是你的工作负荷的国王,你可能需要回到12 MB的芯片。

超线程最多只是将操作系统从操作系统中撤出并将其置于死亡状态,直接访问L1和L2caching的一种方式,这使得任务切换更快。

使用VMWare进行testing表明,禁用HT在标准负载下没有明显区别,在重负载下增加了5%,这是因为ESXi足够聪明,可以知道“真实”线程和“假”线程之间的差别(除此之外,还有更多的东西,但是这是从内部来讲的)。 SQL Server 2005并不是那么聪明,但它与最新的操作系统相结合,禁用HT应该没什么优势。

所有这一切,我同意罗纳德,这很可能是你的二级caching。 caching大小下降33%是相当大的,当我们指定我们的SQL服务器时,我们总是每次都以原始时钟速度进行caching。

根据我的经验,HT在Windows 2008 R2集群(运行SQL Server 2008 R2)上运行我的活动节点上的I / O操作。 一个有趣的事实是,它没有反映在等待统计资料,也没有在微软支持的pssdiag。

我注意到低I / O的方式只是通过观察物理磁盘的操作系统计数器。 正如萨姆指出的那样,我在这里和这里写下了它

如果您没有遇到I / O问题,并且CPU绑定,我build议您以这种方式开始:

查明哪些进程和T-SQL块导致CPU利用率最高。 根据我们的经验,在解决了I / O问题(closuresHT)之后,我们确定了在2008 R2中performance可怕的代码,并在2005年做得很好。我在这里写了这个代码。

在高负荷下运行Adam Machanic的sp_whoisactive。 你可以从这里下载。 由于非常糟糕的计划,由于逻辑读取量过高(每次查询2000万次),我们正在经历非常高的CPU利用率。 我们的stream程使用分区表进行反半连接。

我的下一个build议是运行分析器来识别一组高于CPU和I / O逻辑读取的T-SQL代码。

通过上述步骤,我们能够调整有问题的stream程,并从85%的持续CPU利用率几乎为零。

好运气,请随时给我一个线,如果你find一个修复,因为我想将案件添加到我的博客。

谢谢

奥斯卡

HT是好还是坏都难以确定。

它确实取决于基于经验和阅读的服务器负载模式。 也就是说,当它影响到性能的时候,它会非常糟糕,否则你不会注意到它。

我读到的理论是线程共享caching,这意味着在不利条件下,每个线程都可以覆盖另一个线程的caching。 如果你没有太多的并行性,或者你的负载是很多短的查询,那么它可能不会影响你。

我已经尝试过使用MAXDOP和处理器关系(回到我在SQL Server 2000上的最后一个真正的DBAangular色中),但是决不会发现任何结论性的东西,但是仅限于当时的我的商店。

作为一个快速testing,您可以将处理器关联设置为仅使用物理核心(较低的数字),然后查看会发生什么情况。

但是,至多你失去了一半的核心。 现在可能与我前几年比赛时的情况并不重要,当时是2比4还是4比8。现在是8比16或16比32。

编辑: 斯拉瓦奥克斯的testing

不幸的是,我不认为你会得到更明确的答案,而不是“尝试关注超线程,看看是否有帮助”。

尽pipeJonathan在我的原始主题(你在你的问题中提到了这个问题)提供了有用的答案,但我从来没有得到任何关于HT在我正在研究的特定服务器上的影响的明确证据。 在我的情况下,服务器已经预定要更换,所以我们只是让这些replace“照顾这个问题”可以这么说。

我的build议:

尝试将服务器级别的MAX并行度设置为1 。 SQL上的并行性对于更大,更长时间运行的查询来说是非常有用的,而且你的负载(我假设)无论如何都包含大量较小的查询。 这应该完全消除CXPACKET等待。 这可能会使某些个别查询稍微运行一段时间,但应该允许在服务器上进行更多的“吞吐量”查询。

我在OLTP服务器上做了这个很好的结果。 其他types的服务器(报告服务器,处理服务器,数据仓库)绝对需要将MAXD​​OP设置得更高。

而要清楚的是,这个设置仍然允许SQL在JOIN中为每个单独的表使用多个线程,所以你并不是完全消除了并行性。

至less值得一试,因为此设置更改立即生效,甚至不需要您重新启动SQL服务: http : //msdn.microsoft.com/en-us/library/ms181007.aspx
这意味着如果事情开始恶化,你可以立即将其切换回来。

closuresBIOS中的超线程将需要重新启动服务器,所以风险更大一些。

为了logging,服务器升级后,我们的性能也出乎意料的糟糕。 原来,这是由于BIOS和CPU的省电问题。 服务器(HP)上的默认设置是忽略CPU速度的操作系统控制,并使用自己的algorithm。 将其更改为操作系统控制并更新BIOS后,显着改进。 有一些发行说明(现在找不到)有一个BIOS错误,将CPUlocking在最低性能状态。

https://serverfault.com/a/196329/6390