web-dev-qa-db-fra.com

Utilisation de la mémoire par SQL Server

Comment vérifier l'utilisation de la mémoire par mon serveur SQL dans la zone de production. J'utilise SQL Server 2016.Lorsque je vérifie le gestionnaire de tâches, il s'affiche au-dessus de 90%. Je ne pense pas que ce soit la véritable utilisation de la mémoire par le serveur SQL.

J'ai un outil de performance SQL grafana qui montre l'utilisation du processeur très inférieure à ce que je vois dans le gestionnaire de tâches. J'ai vérifié le moniteur de ressources, il peut voir la valeur moyenne du processeur. Je ne sais pas quelle est l'utilisation de la mémoire du serveur SQL. J'essaie de déterminer si la pression de la mémoire est un problème pour certains de mes problèmes.

Quelqu'un peut-il diriger vers une bonne/bonne explication?.

11
user9516827

Quelqu'un peut-il diriger vers une bonne/bonne explication?.

Je commencerais par dire que le Gestionnaire des tâches n'est pas un endroit correct pour évaluer la consommation de mémoire de SQL Server, il ne vous indiquera pas la valeur correcte lorsque le compte de service SQL Server a le privilège LPIM (Locked Pages in Memory). En effet, normalement, le gestionnaire de tâches suit Process Private bytes qui est de la mémoire paginable et allouée via la fonction VirtualAlloc () mais avec un compte de service ayant une portion LPIM d'allocation de mémoire se fait par API AWE qui est NON paginable, donc le gestionnaire de tâches le fait ne le suit pas et cela peut conduire à une valeur incorrecte.

Il est tout à fait normal que SQL Server utilise la mémoire qui lui est allouée, ce qui semble souvent utiliser une mémoire élevée, mais cela est tout à fait normal. Ne paniquez pas si certains outils affichent une faible utilisation du processeur et que le gestionnaire de tâches affiche une mémoire élevée, cela peut être tout à fait normal. Pour connaître la quantité de mémoire physique utilisée par SQL Server, veuillez utiliser la requête ci-dessous

select
(physical_memory_in_use_kb/1024)Phy_Memory_usedby_Sqlserver_MB,
(locked_page_allocations_kb/1024 )Locked_pages_used_Sqlserver_MB,
(virtual_address_space_committed_kb/1024 )Total_Memory_UsedBySQLServer_MB,
process_physical_memory_low,
process_virtual_memory_low
from sys. dm_os_process_memory

Phy_Memory_usedby_Sqlserver_MB - Donne la mémoire physique totale utilisée par SQL Server en Mo Total_Memory_usedBy_SQLServer_MB - - Donne la mémoire totale (RAM + fichier d'échange) utilisée par SQL Server en Mo

Pour en savoir plus sur les raisons pour lesquelles le gestionnaire de tâches ne doit pas être utilisé, voir Fun with Locked Pages, AWE, Task Manager, and the Working Set…

12
Shanky

"J'essaie de déterminer si la pression de la mémoire est un problème pour certains de mes problèmes."

script très utile: https://github.com/ktaranov/sqlserver-kit/blob/master/Scripts/SQLServer_Memory_Information.sql

vous voyez l'utilisation de la mémoire verbeuse: enter image description here

https://www.sqlskills.com/blogs/glenn/sql-server-diagnostic-information-queries-for-november-2017/ Requêtes d'informations de diagnostic SQL Server 2017:
voir le commentaire

-- Page Life Expectancy (PLE) value for each NUMA node in current instance  (Query 46) (PLE by NUMA Node)
SELECT @@SERVERNAME AS [Server Name], RTRIM([object_name]) AS [Object Name], instance_name, cntr_value AS [Page Life Expectancy]
FROM sys.dm_os_performance_counters WITH (NOLOCK)
WHERE [object_name] LIKE N'%Buffer Node%' -- Handles named instances
AND counter_name = N'Page life expectancy' OPTION (RECOMPILE);
------

-- PLE is a good measurement of internal memory pressure
-- Higher PLE is better. Watch the trend over time, not the absolute value

(Requête 14)

-- Good basic information about OS memory amounts and state  (Query 14) (System Memory)
SELECT total_physical_memory_kb/1024 AS [Physical Memory (MB)], 
       available_physical_memory_kb/1024 AS [Available Memory (MB)], 
       total_page_file_kb/1024 AS [Total Page File (MB)], 
       available_page_file_kb/1024 AS [Available Page File (MB)], 
       system_cache_kb/1024 AS [System Cache (MB)],
       system_memory_state_desc AS [System Memory State]
FROM sys.dm_os_sys_memory WITH (NOLOCK) OPTION (RECOMPILE);
------

-- You want to see "Available physical memory is high" for System Memory State
-- This indicates that you are not under external memory pressure

-- Possible System Memory State values:
-- Available physical memory is high
-- Physical memory usage is steady
-- Available physical memory is low
-- Available physical memory is running low
-- Physical memory state is transitioning

(47)

-- Memory Grants Pending value for current instance  (Query 47) (Memory Grants Pending)
SELECT @@SERVERNAME AS [Server Name], RTRIM([object_name]) AS [Object Name], cntr_value AS [Memory Grants Pending]
FROM sys.dm_os_performance_counters WITH (NOLOCK)
WHERE [object_name] LIKE N'%Memory Manager%' -- Handles named instances
AND counter_name = N'Memory Grants Pending' OPTION (RECOMPILE);
------

-- Run multiple times, and run periodically if you suspect you are under memory pressure
-- Memory Grants Pending above zero for a sustained period is a very strong indicator of internal memory pressure

(62)

-- Top Cached SPs By Total Logical Reads. Logical reads relate to memory pressure  (Query 62) (SP Logical Reads)
SELECT TOP(25) p.name AS [SP Name], qs.total_logical_reads AS [TotalLogicalReads], 
qs.total_logical_reads/qs.execution_count AS [AvgLogicalReads],qs.execution_count, 
ISNULL(qs.execution_count/DATEDIFF(Minute, qs.cached_time, GETDATE()), 0) AS [Calls/Minute], 
qs.total_elapsed_time, qs.total_elapsed_time/qs.execution_count AS [avg_elapsed_time],
CASE WHEN CONVERT(nvarchar(max), qp.query_plan) LIKE N'%<MissingIndexes>%' THEN 1 ELSE 0 END AS [Has Missing Index], 
FORMAT(qs.last_execution_time, 'yyyy-MM-dd HH:mm:ss', 'en-US') AS [Last Execution Time], 
FORMAT(qs.cached_time, 'yyyy-MM-dd HH:mm:ss', 'en-US') AS [Plan Cached Time]
-- ,qp.query_plan AS [Query Plan] -- Uncomment if you want the Query Plan
FROM sys.procedures AS p WITH (NOLOCK)
INNER JOIN sys.dm_exec_procedure_stats AS qs WITH (NOLOCK)
ON p.[object_id] = qs.[object_id]
CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) AS qp
WHERE qs.database_id = DB_ID()
AND DATEDIFF(Minute, qs.cached_time, GETDATE()) > 0
ORDER BY qs.total_logical_reads DESC OPTION (RECOMPILE);
------

-- This helps you find the most expensive cached stored procedures from a memory perspective
-- You should look at this if you see signs of memory pressure

(63)

-- Top Cached SPs By Total Physical Reads. Physical reads relate to disk read I/O pressure  (Query 63) (SP Physical Reads)
SELECT TOP(25) p.name AS [SP Name],qs.total_physical_reads AS [TotalPhysicalReads], 
qs.total_physical_reads/qs.execution_count AS [AvgPhysicalReads], qs.execution_count, 
qs.total_logical_reads,qs.total_elapsed_time, qs.total_elapsed_time/qs.execution_count AS [avg_elapsed_time],
CASE WHEN CONVERT(nvarchar(max), qp.query_plan) LIKE N'%<MissingIndexes>%' THEN 1 ELSE 0 END AS [Has Missing Index],
FORMAT(qs.last_execution_time, 'yyyy-MM-dd HH:mm:ss', 'en-US') AS [Last Execution Time], 
FORMAT(qs.cached_time, 'yyyy-MM-dd HH:mm:ss', 'en-US') AS [Plan Cached Time]
-- ,qp.query_plan AS [Query Plan] -- Uncomment if you want the Query Plan 
FROM sys.procedures AS p WITH (NOLOCK)
INNER JOIN sys.dm_exec_procedure_stats AS qs WITH (NOLOCK)
ON p.[object_id] = qs.[object_id]
CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) AS qp
WHERE qs.database_id = DB_ID()
AND qs.total_physical_reads > 0
ORDER BY qs.total_physical_reads DESC, qs.total_logical_reads DESC OPTION (RECOMPILE);
------

-- This helps you find the most expensive cached stored procedures from a read I/O perspective
-- You should look at this if you see signs of I/O pressure or of memory pressure

(64)

-- Top Cached SPs By Total Logical Writes (Query 64) (SP Logical Writes)
-- Logical writes relate to both memory and disk I/O pressure 
SELECT TOP(25) p.name AS [SP Name], qs.total_logical_writes AS [TotalLogicalWrites], 
qs.total_logical_writes/qs.execution_count AS [AvgLogicalWrites], qs.execution_count,
ISNULL(qs.execution_count/DATEDIFF(Minute, qs.cached_time, GETDATE()), 0) AS [Calls/Minute],
qs.total_elapsed_time, qs.total_elapsed_time/qs.execution_count AS [avg_elapsed_time],
CASE WHEN CONVERT(nvarchar(max), qp.query_plan) LIKE N'%<MissingIndexes>%' THEN 1 ELSE 0 END AS [Has Missing Index], 
FORMAT(qs.last_execution_time, 'yyyy-MM-dd HH:mm:ss', 'en-US') AS [Last Execution Time], 
FORMAT(qs.cached_time, 'yyyy-MM-dd HH:mm:ss', 'en-US') AS [Plan Cached Time]
-- ,qp.query_plan AS [Query Plan] -- Uncomment if you want the Query Plan 
FROM sys.procedures AS p WITH (NOLOCK)
INNER JOIN sys.dm_exec_procedure_stats AS qs WITH (NOLOCK)
ON p.[object_id] = qs.[object_id]
CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) AS qp
WHERE qs.database_id = DB_ID()
AND qs.total_logical_writes > 0
AND DATEDIFF(Minute, qs.cached_time, GETDATE()) > 0
ORDER BY qs.total_logical_writes DESC OPTION (RECOMPILE);
------

-- This helps you find the most expensive cached stored procedures from a write I/O perspective
-- You should look at this if you see signs of I/O pressure or of memory pressure

P.S. ce n'est pas une réponse exhaustive

17
Igor

Je ne suis pas sûr de l'outil grafana, mais si vous exécutez la requête ci-dessous, il affiche la mémoire actuellement allouée

SELECT  
(physical_memory_in_use_kb/1024) AS Memory_usedby_Sqlserver_MB,  
(locked_page_allocations_kb/1024) AS Locked_pages_used_Sqlserver_MB,  
(total_virtual_address_space_kb/1024) AS Total_VAS_in_MB,  
process_physical_memory_low,  
process_virtual_memory_low  
FROM sys.dm_os_process_memory; 
2
Goforebroke

Vous devez ignorer le gestionnaire de tâches car il ne rend pas correctement compte des informations d'allocation de mémoire dans certains cas, en fonction des routines d'allocation de mémoire utilisées par l'application. Depuis le système d'exploitation, vous devriez être bon avec perfmon, car il doit signaler correctement l'utilisation de la mémoire. Vous pouvez également utiliser des DMV SQL rapportant des informations sur la mémoire, par ex. sys.dm_os_sys_memory (il y a plus de dmv liés à la mémoire selon vos besoins et la version de SQL Server).

Voici un article expliquant le gestionnaire de tâches signalant de manière inexacte l'utilisation de memroy SQL Server:

LIEN: arrêtez d'utiliser le gestionnaire de tâches pour vérifier l'utilisation de la mémoire sqls

0
Błażej Ciesielski