Дедлок с повторной блокировкой ресурса (ms sql 2014)

Столкнулся со следующим дедлоком:

<deadlock-list>
  <deadlock victim="process233c64ffc28">
    <process-list>
      <process id="process233c64ffc28" taskpriority="0" logused="0" waitresource="KEY: 39:72057594166247424 (c0af60d834ba)" waittime="23" ownerId="775457003509" transactionname="MERGE" lasttranstarted="2021-08-05T16:10:03.740" XDES="0x1d12ad5ed10" lockMode="U" schedulerid="25" kpid="181500" status="suspended" spid="4722" sbid="0" ecid="0" priority="0" trancount="2" lastbatchstarted="2021-08-05T16:10:00.877" lastbatchcompleted="2021-08-05T16:10:00.877" lastattention="1900-01-01T00:00:00.877" clientapp="SQLAgent - TSQL JobStep (Job 0x6B29890337552344A9872086DCFB22A9 : Step 2)" hostname="XXX" hostpid="86268" loginname="stc\XXX" isolationlevel="read committed (2)" xactid="775457003509" currentdb="39" currentdbname="DBNAME" lockTimeout="4294967295" clientoption1="673185824" clientoption2="128056">
        <executionStack>
          <frame procname="sp1" line="171" stmtstart="10646" stmtend="11194" sqlhandle="0x0300270074aa560a0d4cbb0026a9000001000000000000000000000000000000000000000000000000000000">
MERGE INTO Tbl1 Tgt
    USING (
        SELECT DISTINCT F.Id, F.PV
        FROM dbo.TblF F
        INNER JOIN @TblAF A
        ON A.Id = F.Id) AS Src
    ON Tgt.FId = Src.Id
    WHEN NOT MATCHED THEN
        INSERT(FId, FType)
        VALUES(Src.Id, Src.PV)     </frame>
          <frame procname="DBName.sp2" line="11" stmtstart="746" stmtend="804" sqlhandle="0x03002700ee9019648e33d900c5a8000001000000000000000000000000000000000000000000000000000000">
exec sp1     </frame>
          <frame procname="adhoc" line="1" sqlhandle="0x01002700689c3a2a803694979e01000000000000000000000000000000000000000000000000000000000000">
exec sp2     </frame>
        </executionStack>
        <inputbuf>
exec sp2    </inputbuf>
      </process>
      <process id="process20539cb7848" taskpriority="0" logused="1048" waitresource="KEY: 39:72057594166247424 (c10f927342d3)" waittime="24" ownerId="775457003788" transactionname="DELETE" lasttranstarted="2021-08-05T16:10:03.743" XDES="0xd8bd4e03b0" lockMode="U" schedulerid="27" kpid="198392" status="suspended" spid="4564" sbid="0" ecid="0" priority="0" trancount="2" lastbatchstarted="2021-08-05T16:10:01.277" lastbatchcompleted="2021-08-05T16:10:01.277" lastattention="1900-01-01T00:00:00.277" clientapp="SQLAgent - TSQL JobStep (Job 0x0C3A444DF8D29A47AC800279A54E8CDB : Step 2)" hostname="XXX" hostpid="86268" loginname="stc\XXX" isolationlevel="read committed (2)" xactid="775457003788" currentdb="39" currentdbname="DBNAME" lockTimeout="4294967295" clientoption1="673185824" clientoption2="128056">
        <executionStack>
          <frame procname="DBName.sp3" line="44" stmtstart="2634" stmtend="2736" sqlhandle="0x03002700ab98f9329c5ab0004fad000001000000000000000000000000000000000000000000000000000000">
DELETE FROM Tbl1 WHERE Processed =     </frame>
          <frame procname="adhoc" line="1" sqlhandle="0x01002700f8771d14c08ca1dbc201000000000000000000000000000000000000000000000000000000000000">
exec sp3     </frame>
        </executionStack>
        <inputbuf>
exec sp3    </inputbuf>
      </process>
    </process-list>
    <resource-list>
      <keylock hobtid="72057594166247424" dbid="39" objectname="DBName.Tbl1" indexname="PK_FId" id="lock9286e26580" mode="X" associatedObjectId="72057594166247424">
        <owner-list>
          <owner id="process20539cb7848" mode="X" />
        </owner-list>
        <waiter-list>
          <waiter id="process233c64ffc28" mode="U" requestType="wait" />
        </waiter-list>
      </keylock>
      <keylock hobtid="72057594166247424" dbid="39" objectname="DBName.Tbl1" indexname="PK_FId" id="lock1160ba17800" mode="U" associatedObjectId="72057594166247424">
        <owner-list>
          <owner id="process233c64ffc28" mode="U" />
        </owner-list>
        <waiter-list>
          <waiter id="process20539cb7848" mode="U" requestType="wait" />
        </waiter-list>
      </keylock>
    </resource-list>
  </deadlock>
</deadlock-list>

версия сервера: Microsoft SQL Server 2014 (SP3-CU4) (KB4500181) - 12.0.6329.1 (X64) Jul 20 2019 21:42:29 Copyright (c) Microsoft Corporation Enterprise Edition (64-bit) on Windows NT 6.3 (Build 9600: )

Может кто объяснить, как так получается, что на один и тот же ресурс в одном процессе два раза одна и та же блокировка( в данном случае U). И как устранять такого рода дедлоки?

UPD

Я вижу в resource-list два раза keylock hobtid="72057594166247424" из чего я делаю вывод, что это один и тот же ресурс (PK для таблицы). Затем в первом <keylock я вижу , что процесс process20539cb7848 уже получил X блокировку на этот ресурс. А в следующем <keylock вижу, что тот же процесс (process20539cb7848) просит U блокировку на ресурс. Т.е. процесс process20539cb7848 имея X блокировку на ресурс keylock hobtid="72057594166247424" запрашивает U блокировку на ресурс. Что это значит? В каком случает после получения X блокировки может потребоваться запросить U блокировку, разве U блокировка, не накладывается перед X блокировкой?


Ответы (0 шт):