zoukankan      html  css  js  c++  java
  • sql server 性能调优之 资源等待内存瓶颈的三种等待类型

    一.概述

      这篇介绍Stolen内存相关的主要三种等待类型以及对应的waittype编号,CMEMTHREAD(0x00B9),SOS_RESERVEDMEMBLOCKLIST(0x007B),RESOURCE_SEMAPHORE_QUERY_COMPILE(0x011A)。也可以通过sysprocesses里查看连接处于某个等待状态, waittype!=0x0000。

    select * from sys.sysprocesses where waittype!=0x0000 and spid>50

       再次看下Stolen内存的分配场景:

    1. CMEMTHREAD内存 

      cmemthread是指多个用户同时往同一块缓存里申请或释放内存时,在一个时间点上, 只有一个连接可以做申请或释放内存动作, 其他连接必须等待。原因:出现这种等待的原因通常是发生在并发度非常高的sqlserver里,而这些并发的连接,在大量地使用需要每次都做编译的动态t-sql语句。 解决:修改客户连接行为,尽可能更多地使用存储过程, 或者使用参数化的t-sql语句,减少语句编译量增加执行计划的重用,避免大量连接同时申请内存做语句编译的现象。

        在生产环境下cmemthread平均每次请求时间为0.20ms(1570876.0/7825922.0=0.20)

    2.SOS_RESERVEDMEMBLOCKLIST

      sos_reservedmemblocklist是指当用户要申请MemtoLeave这块内存时而暂时不能满足就会出现等待。原因:当用户发过来的语句内含有大量参数,或者有一个in 子句,它的执行计划在8kb的singlepage里可能放不下,需要用multi-page来存储。当缓存的执行计划越来越多,multi-page里的内存也会越来越多。 解决:(1)避免使用带有大量参数或者长in子句的语句,这种语句需要消耗比正常语句更多的内存及cpu资源, 改变的方法是可以把参数值存储到临时表,用join来连接。(2)定期运行dbcc freeproccache 语句,手工清除缓存中的执行计划,缓存内存压力。

    -- 查看缓存占用空间
    SELECT SUM(CONVERT(DECIMAL(18,4),size_in_bytes))/1024.0/1024.0 AS 'sizeMB'
    FROM sys.dm_exec_cached_plans
    --查看缓存中的对象类型,重用次数,sql语句,缓存空间大小,可以根据几个维度来统计
    SELECT  usecounts,size_in_bytes/1024.0 AS 'sizeKB',cacheobjtype,objtype,[text] 
    FROM sys.dm_exec_cached_plans 
    CROSS APPLY sys.dm_exec_sql_text(plan_handle) 
    WHERE usecounts > 1  
    ORDER BY usecounts DESC

      

    3.RESOURCE_SEMAPHORE_QUERY_COMPILE

       resource_semaphore_query_compile是指:当编译的语句需要的内存达到了sqlserver的编译内存上限时(sqlserver会为编译内存设置一个上限),其它语句将进入等待状态,等前面的语句编译完成,把内存释放出来以后,后面的语句才能继续编译。解决(1)修改客户连接行为,尽可能更多地使用存储过程, 或者使用参数化的t-sql语句,减少语句编译量,增加执行计划的重用,避免大量连接同时申请内存做语句编译的现象.(2)简化每次需要编译语句的复杂度,降低编译需要的内存量。(3)当stolen 内存使用总量比较大的时候,也可以定期执行dbcc freeproccache 。

    总结:以上三种等待类型,当缓存的执行计划越来越多,存放buffer pool里的stolen内存在不断增长,当需要的内存超过8kb时,multi-page里的存储执行计划stolen内存也会越来越多 。能过sys.sysprocess.waittype字段,可以检查stolen内存上是否有瓶颈。通过sql server 内存初探 知道 sql server里的Consumer下的功能组件,第三方代码,线程都是能过stolen方式直接提交,并不需要先申请内存。

      查看内存使用情况

    -- 按申请方式统计内存 (Reserve 再commit)(直接commit叫Stolen)   
    SELECT 
    SUM(virtual_memory_reserved_kb)/1024.0 AS 'reserved(MB)',
    SUM(virtual_memory_committed_kb)/1024.0 AS 'committed(MB)',
    (SUM(single_pages_kb)+SUM(multi_pages_kb))/1024.0 AS 'Stolen(MB)'
     FROM sys.dm_os_memory_clerks
     
     -- 按申请内存页大小统计内存    
    SELECT 
    (SUM(virtual_memory_committed_kb)+SUM(single_pages_kb))/1024.0 AS 'Buffer Pool(MB)',
    SUM(multi_pages_kb)/1024.0 AS 'MemToLeave(MB)'
     FROM sys.dm_os_memory_clerks

       按申请方式统计内存,共申请了92576MB,提交了83621MB, 在Stolen中有9244MB。 如下图所示:

      按申请内存页大小(<=8kb  >8kb)统计内存:
      

  • 相关阅读:
    解决PKIX:unable to find valid certification path to requested target 的问题
    Linux 上的常用文件传输方式介绍与比较
    用VNC远程图形化连接Linux桌面的配置方法
    红帽中出现”This system is not registered with RHN”的解决方案
    linux安装时出现your cpu does not support long mode的解决方法
    CentOS SSH配置
    es6扩展运算符及rest运算符总结
    es6解构赋值总结
    tortoisegit安装、clon、推送
    es6环境搭建
  • 原文地址:https://www.cnblogs.com/MrHSR/p/9350174.html
Copyright © 2011-2022 走看看