I want to capture SQL Server queries with a memory grant over 10 GB so those queries and the tables they touch can be tuned to reduce the memory grants. I created an extended events session and a test query that should have been captured in the extended events file. However, the xEvents session isn't capturing anything.
As a troubleshooting step, I lowered the memory grant value for a query to 10 KB so I knew the xEvent session would be sure to capture activity in the file. However, that still didn't solve my issue.
CREATE EVENT SESSION [CaptureLargeMemoryGrants] ON SERVER
ADD EVENT sqlserver.query_memory_grants
(ACTION(sqlserver.client_app_name,sqlserver.client_hostname,sqlserver.database_name,sqlserver.sql_text,sqlserver.username)
WHERE ([granted_memory_kb]>(10)
)
)
ADD TARGET package0.event_file(SET filename=N'C:\Program Files\Microsoft SQL Server\MSSQL16.SQL2022\MSSQL\Log\CaptureLargeMemoryGrants.xel')
WITH (MAX_MEMORY=4096 KB,EVENT_RETENTION_MODE=ALLOW_SINGLE_EVENT_LOSS,MAX_DISPATCH_LATENCY=30 SECONDS,MAX_EVENT_SIZE=0 KB,MEMORY_PARTITION_MODE=NONE,TRACK_CAUSALITY=OFF,STARTUP_STATE=ON)
GO
I wrote this test query:
--test query that has a sufficient memory grant to be captured:
USE StackOverflow2013;
GO
SELECT TOP (6000000) U.DisplayName
,U.Location
,U.Reputation
,P.title
,p.CreationDate
,p.ClosedDate
,p.ViewCount
,PT.Type
FROM dbo.users AS U
LEFT JOIN dbo.Posts AS P ON P.OwnerUserId = U.Id
INNER JOIN dbo.PostTypes AS PT ON P.PostTypeId = PT.Id
OPTION (RECOMPILE);
I can tell from both of these queries below that my test query has a sufficient memory grant that it should be captured. I'm not sure what I'm missing. I assume I must have the wrong event in my xEvents session, but I'm not sure what else I should be using.
SELECT query_stats.query_hash
,query_stats.query_plan_hash
,SUBSTRING(sql_text.TEXT, 1, 1000) AS QueryText
,-- Limit text length for readability
query_stats.max_grant_kb
,query_stats.max_used_grant_kb
FROM sys.dm_exec_query_stats AS query_stats
CROSS APPLY sys.dm_exec_sql_text(query_stats.sql_handle) AS sql_text
ORDER BY query_stats.max_grant_kb DESC;
SELECT r.session_id
,r.granted_query_memory
,r.STATUS
,r.command
,t.TEXT
FROM sys.dm_exec_requests r
JOIN sys.dm_exec_sessions s ON r.session_id = s.session_id
CROSS APPLY sys.dm_exec_sql_text(r.sql_handle) t
WHERE r.granted_query_memory > 0;
