Following up on my other question here, I'd like an easy way to visualize the answer.
I've tried using a query like this, but the number of "running" threads can exceed DOP sometimes.
SELECT ost.session_id,
ost.exec_context_id,
ost.scheduler_id,
qp.node_id,
w.worker_address,
qp.physical_operator_name,
ost.task_state,
qp.row_count
FROM sys.dm_os_tasks AS ost
JOIN sys.dm_os_workers AS w
ON ost.worker_address = w.worker_address
LEFT JOIN sys.dm_exec_query_profiles AS qp
ON w.task_address = qp.task_address
WHERE ost.session_id = 57
AND ost.task_state = 'RUNNING'
ORDER BY ost.exec_context_id, ost.scheduler_id, qp.node_id, w.worker_address;
I've also tried using the query_thread_profile
Extended Event, but for a plan with multiple parallel branches, it shows the same N number of Thread IDs. This seems contrary to the answer given, since DOP doesn't explicitly limit the total number of threads used. For a query running at DOP 4, it looks like this. I'm sure that the same four threads (plus coordinator) don't get used for all branches and operators.
So like, running a query like this at DOP 8 gives me three parallel branches.
SELECT COUNT(DISTINCT t1.Data)
FROM dbo.t1
JOIN dbo.t2
ON t1.Id = t2.f_Id
JOIN t3
ON t1.Id = t3.f_Id
OPTION(FORCE ORDER, HASH JOIN);
But sometimes my query returns this:
And sometimes it returns this:
Here's some sample data:
CREATE TABLE dbo.t1 ( Id INT IDENTITY PRIMARY KEY CLUSTERED, Data INT NOT NULL );
CREATE TABLE dbo.t2 ( Id INT IDENTITY PRIMARY KEY CLUSTERED, f_Id INT NOT NULL );
CREATE TABLE dbo.t3 ( Id INT IDENTITY PRIMARY KEY CLUSTERED, f_Id INT NOT NULL );
INSERT dbo.t1 WITH (TABLOCKX) ( Data )
SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) % 2000
FROM (
SELECT TOP 1000000 1 AS num
FROM master..spt_values AS sv
CROSS JOIN master..spt_values AS sv2
CROSS JOIN master..spt_values AS sv3
) AS nums
INSERT dbo.t2 WITH (TABLOCKX) ( f_Id )
SELECT TOP 15000000 t.Id
FROM dbo.t1 AS t
CROSS JOIN dbo.t1 AS t2
INSERT dbo.t3 WITH (TABLOCKX) ( f_Id )
SELECT TOP 25000000 t.Id
FROM dbo.t1 AS t
CROSS JOIN dbo.t1 AS t2
Thanks!