Sch-M WAIT, SQL Server 2014'te Sch-S'yi engeller, ancak SQL Server 2008 R2'yi engellemez mi?


11

Kısa bir süre önce üretim örneklerimizi SQL 2008 R2'den yeni SQL 2014 sunucularına taşıdık. Hizmet Aracısı kullanımımızla ortaya çıkardığımız ilginç bir senaryo. İçeren bir veri tabanı düşünün Broker Enabled = trueile MyServiceve MyQueue. Bu kuyrukta zehirli mesaj işleme devre dışı bırakıldı. Kuyrukta mesajlar içeren en az 2 aktif görüşme vardır.

Bir işlemde (SPID 100) şunları yürütün:

BEGIN TRANSACTION;
DECLARE @conversation_group_id UNIQUEIDENTIFIER;
RECEIVE TOP (1) @conversation_group_id = conversation_handle FROM MyQueue;

İşlemi açık bıraktığımızı unutmayın. Bazı harici kaynaklarda uzun süre bekleyen bir .NET programı olduğunu düşünün. Via sys.dm_tran_locksbu SPID kuyruğunda bir IX kilidi verilmiş olduğunu görüyoruz.

| type   | resource_id | mode | status | spid |
| OBJECT | 277576027   | IX   | GRANT  | 100  |

Ayrı bir işlemde (SPID 101) beş kez yürütün :

BEGIN TRANSACTION;
DECLARE @conversation_group_id UNIQUEIDENTIFIER;
RECEIVE TOP (1) @conversation_group_id = conversation_handle FROM MyQueue;
ROLLBACK TRANSACTION;

Buradaki anahtar, işlemi beş kez geri almamızdır . Bu yerleşik Zehir Mesaj İşleme arka plan mantığını tetikler . Kuyruk devre dışı bırakılmasa da (devre dışı bırakılmayacak şekilde yapılandırıldığı için), arka plan görevi hala bir iş yapmaya ve bir broker_queue_disabledolayı başlatmaya çalışıyor . Şimdi sys.dm_tran_lockstekrar sorgularsak BRKR TASK, bir Sch-M kilidinde bekleyen farklı bir SPID (ile ilişkili ) göreceğiz .

| type   | resource_id | mode  | status | spid |
| OBJECT | 277576027   | IX    | GRANT  | 100  |
| OBJECT | 277576027   | Sch-M | WAIT   | 36   |

Şimdiye kadar her şey mantıklı.

Son olarak, farklı bir işlemde (SPID 102), bu Kuyruğu kullanarak bir Hizmete GÖNDERMEYİ deneyin:

BEGIN TRANSACTION;
DECLARE @ch uniqueidentifier;
BEGIN DIALOG @ch FROM SERVICE [MyService] TO SERVICE 'MyService';
SEND ON CONVERSATION @ch ('HELLO WORLD');

SENDKomut engellendi. Tekrar sys.dm_tran_locksbakarsak, bu sürecin bir Sch-S kilidinde beklediğini görürüz. Yürütülmesi sp_who2biz SPID 102 SPID 36 tarafından engellenir bulmak.

| type   | resource_id | mode  | status | spid |
| OBJECT | 277576027   | IX    | GRANT  | 100  |
| OBJECT | 277576027   | Sch-M | WAIT   | 36   |
| OBJECT | 277576027   | Sch-S | WAIT   | 102  |

Sch-S kilidi neden bekleyen Sch-M kilidini bekliyor?

Bu davranış, SQL 2008 R2'de tamamen farklıdır! Bizim üzerinde çalışan, bu aynı senaryoyu kullanarak 2008R2 örneklerini içeren nihai yığın henüz-to-hizmet dışı bırakılmış SENDkomuta etmez bekleyen Sch-M kilit tarafından engellenir.

SQL 2012 veya 2014'te kilitleme davranışı değişti mi? Bu kilitleme davranışını etkileyebilecek bazı veritabanı veya sunucu ayarları var mı?


Olası bir hata gibi geliyor. En son SP ve CU'ları uyguladınız mı?
Max Vernon

1
MaxVernon 12.00.2370
Joseph Daigle

3
Başlatıcı ve hedefle aynı hizmeti kullanıyorsunuz. SENDBloklar kontrol ederken başlatıcı kuyruğu. hedef kuyruğu SENDengellemezse, hemen sıçrar ve dağıtım için kullanır . Eğer ikisini ayırırsanız (her zaman iyi bir fikir) sorun olmazdı. sys.transmission_queue
Remus Rusanu

1
Teşekkürler @ RemusRusanu. Bu örnek kısmen değişen davranışı göstermek için kısmen de olsa, ipucumuz hizmetlerimizi ve kuyruklarımızı tasarlarken aklımızda tutacağımız bir örnek.
Joseph Daigle

Yanıtlar:


17

Davranış SQL Server 2008 R2 ve SQL Server 2012 arasında değişti. 2008 R2 uygulaması, belgelenmiş 'rahat FIFO' semantiği ile tutarsızdı :

Kilitler rahat bir ilk giren ilk çıkar (FIFO) tarzında verilir. Sipariş katı FIFO olmamasına rağmen, açlıktan kaçınma gibi arzu edilen özellikleri korur ve gereksiz kilitlenmeleri ve engellemeyi azaltmaya çalışır.

İstenen mod verilen isteklerin birliği ve bekleyen istek modları ile uyumsuzsa, istekte bulunanın henüz kaynak üzerinde bir kilide sahip olmadığı yeni kilit istekleri engellenir.

Bir dönüşüm isteği, yalnızca istenen mod, dönüşüm isteğinin kendisinin orijinal olarak verildiği mod hariç olmak üzere, verilen tüm modların birleşimiyle uyumlu değilse engellenir.

2008 R2'de, Sch-Sverilen açlık ve bekleme taleplerinin birliği ile uyumsuz olmasına rağmen yeni bir kilit talebi verildi ve bu da kilit açlığa neden olabilir. 2012'de Sch-Skilit isteği engellendi.

Aşağıdaki çoğaltma komut dosyası, Service Broker kuyruğu yerine normal tablolar kullanır:

-- Session 1
CREATE TABLE dbo.LockTest (col1 integer NULL);

INSERT dbo.LockTest (col1) VALUES (1);

BEGIN TRANSACTION;

-- Will hold row-X, Pag-IX, and Tab-IX
INSERT dbo.LockTest (col1) VALUES (2);

-- Session 2
-- Blocked waiting on Sch-M
TRUNCATE TABLE dbo.LockTest;

-- Session 3
-- Takes Sch-S only
-- Not blocked in 2008 R2
SELECT * FROM dbo.LockTest AS LT WITH (READUNCOMMITTED);

Özetle, 2008 R2 tasarlandığı gibi davranmamıştır. Sorun SQL Server 2012'de giderildi.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.