![SQL Server 突然只使用了一小部分 CPU](https://linux22.com/image/540071/SQL%20Server%20%E7%AA%81%E7%84%B6%E5%8F%AA%E4%BD%BF%E7%94%A8%E4%BA%86%E4%B8%80%E5%B0%8F%E9%83%A8%E5%88%86%20CPU.png)
我们有一台运行 SQL Server 2008 的 Windows 2008 R2 服务器。突然间,SQLServer 进程拒绝超过 20% 的 CPU 使用率。截至上周,当对数据库运行繁重的查询时,正如我所料,使用率会上升到 100%。我们使用这台服务器已经有一段时间了,它突然有这个限制似乎很奇怪。这个限制导致我们的查询比平时花费的时间长得多。没有人(至少是故意的)对服务器配置进行任何更改。
经过一番调查,我发现了 sys.dm_os_sys_memory 视图。它显示“可用物理内存很高”,但同时可用物理内存为 339552kb,而总内存为 4193848kb。值得注意的是,这是在 vmware 上运行的虚拟服务器。
SQL Server 中是否有某个设置可以设置最大 CPU 使用率?我在资源管理器中找到了该设置,尽管它目前一直处于关闭状态。
我们最近开始使用 Quest Software 的 Spotlight for SQL Server。今天早上,它的播放数据库短暂地位于此服务器上,不久之后我第一次注意到了这个问题,尽管在此之前我没有进行任何查询,所以我不知道问题是否从这里开始,但是数据库在星期五下午按预期运行。Windows 日志显示,在创建 SpotlightPlaybackDatabase 时应用了以下设置。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 TORN_PAGE_DETECTION 设置为 ON。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 MULTI_USER 设置为 ON。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 READ_WRITE 设置为 ON。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 AUTO_UPDATE_STATISTICS 设置为 ON。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 AUTO_CREATE_STATISTICS 设置为 ON。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 ANSI_WARNINGS 设置为 OFF。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 CONCAT_NULL_YIELDS_NULL 设置为 ON。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 RECOVERY 设置为 SIMPLE。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 QUOTED_IDENTIFIER 设置为 OFF。
- 2011 年 2 月 21 日 08:45:02,spid60,未知,将数据库 SpotlightPlaybackDatabase 的数据库选项 AUTO_CLOSE 设置为 OFF。
这些设置更改是否会修改应用于整个服务器的设置?
编辑#1: 通过重新启动 SQL Server 成功修复了这个问题,但一开始并不确定问题是什么。尽管问题已经解决,但我仍需要解决一些我之前没有意识到的 io 问题。
编辑#2: 问题再次出现。解决方案是关闭 SQL Server 上的 Spotlight 中的跟踪分析,这是拖慢一切的原因。
答案1
检查 sys.dm_os_waiting_tasks 并查看等待资源是什么。基本上查看 wait_type 并查看其中的内容。运行此查询并发回结果。
select wait_type, sum(wait_duration_ms) sum_wait_duration_ms, avg(wait_duration_ms) avg_wait_duration_ms, count(*) waits
from sys.dm_os_waiting_tasks
group by wait_type
你可能正在遭受与我今天早上谈到的类似的问题我的博客。
答案2
你无法管理 CPU 使用率,但你可以管理CPU 亲和力。也就是说,有人限制SQL Server只能使用单个CPU吗?
同样,有人改变了全局 maxdop 设置? 这会将所有查询限制在一个 CPU 上,但任何单个查询都将在其中一个可用 CPU 上运行
答案3
假设 CPU 亲和性或 MAXDOP 的配置没有发生改变(如 gbn 所述),那么存在几种可能性。
第一种情况是,由于索引或底层表数据的分布发生了很大变化,导致查询的查询计划发生了变化。尝试优化或重建底层表上的索引。
其次,您现在可能受到 I/O 限制,要么从主数据库文件读取数据,要么在 tempdb 中工作(如果查询的中间部分对于 RAM 来说太大,SQL 会将查询的中间部分存储在其中)。使用 perfmon 并监视平均磁盘队列长度。它的平均长度应小于服务器中的物理磁盘主轴数。如果在“繁重查询”期间 CPU 保持较低水平时队列长度突然增加,则 CPU 只是在等待磁盘 IO,因此无法 100% 地执行有用的工作。如果是这种情况,您有几个选择:更多 RAM(以减少使用磁盘的需要)、更快的磁盘(SSD?),或者优化查询、索引和架构以减少磁盘 IO。最后一个选项的影响可能最大(实际上可以将事情改善 100 倍或更多)。但它也可能是最困难的,具体取决于您的数据结构和查询。阅读 SQL 执行计划;购买一些书籍。
答案4
通过重新启动 SQL Server 解决了这个问题,尽管我不知道最初是什么原因造成的。感谢大家的回复。