I'm running into a deadlock issue on a SQL Server 2008 R2. When looking at the deadlock graph in the SQL Profiler, the problem seems to stem from query notifications :

  <resource-list>
   <keylock hobtid="72057654759522304" dbid="6" objectname="MyDB.sys.query_notification_814081939" indexname="cidx" id="lock15ab2aa80" mode="RangeX-X" associatedObjectId="72057654759522304">
    <owner-list>
     <owner id="process5c5708" mode="RangeX-X"/>
    </owner-list>
    <waiter-list>
     <waiter id="process4e9ae08" mode="RangeS-U" requestType="wait"/>
    </waiter-list>
   </keylock>
   <keylock hobtid="72057654759522304" dbid="6" objectname="MyDB.sys.query_notification_814081939" indexname="cidx" id="lock15e56a300" mode="RangeS-U" associatedObjectId="72057654759522304">
    <owner-list>
     <owner id="process4e9ae08" mode="RangeS-U"/>
    </owner-list>
    <waiter-list>
     <waiter id="process5c5708" mode="RangeS-U" requestType="wait"/>
    </waiter-list>
   </keylock>
  </resource-list>

These query notifications are implemented using SQLDependency. The deadlock seems to be occuring when updating a table which is monitored by the SQLDependency.

I don't really understand the deadlock graph syntax..The KeyLock mode is RangeS-U only while using the serializable transaction isolation level., right ?

I've also read this question... should i activate READ_COMMITED_SNAPSHOT ?

thx...

有帮助吗?

解决方案

Can't pin it down for sure, but here are some thoughts...

The statement that causes the notification may not complete before the notification is delivered. Thus it may still have active locks at the point when the notification is received from service broker and any action is taken on the notification.

Maybe your notification recipient is trying to clean up the queue or get a second notification out of the queue before the transaction that generated the first notification is complete.

Is the DML that generated the notification running in a multi-step transaction? Is the code that receives notifications running in a multi-step transaction. (i.e. did you use begin tran or equivalent?).

It could be useful to track down the processes mentioned in the deadlock graph and understand which code holds the RangeX-X lock and which holds the RangeS-U.

You might want to post some minimal examples of the code that generates a notification and the code that receives it.

Also here is a Microsoft KB about a known somewhat similar deadlock problem with notifications and multiple subscriptions.

MS KB975090 Might be relevant, but not exactly the same.

其他提示

The main cause behind that is the fact that transactions are too long and involve too many objects.

As I said in my question, the table on which the SqlDependency is fired contains a reference to each object in the database. Updating a bunch of objects in the same transaction implies locks on this big table by the query notification system. Hence, you're quickly trapped in a deadlock situation.

2 solutions (advised by MS):

  • Reduce the length and complexity of transactions.
  • Execute the requests triggering the notification system outside big transactions.
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top