Site icon Nhạc lý căn bản – nhacly.com

Deadlock trong sql là gì | HoiCay – Top Trend news

Java tương hỗ lập trình đa luồng ( multithreading ), khi có nhiều thread chạy đồng thời trong một chương trình, trong 1 số ít trường hợp nhất định hoặc do sai xót dẫn đến những thread rơi vào thực trạng chờ mãi mãi. Trong bài viết này, tất cả chúng ta sẽ cùng nhau tìm hiểu và khám phá về Deadlock là gì ? làm thế nào để tránh Deadlock qua những ví dụ trong java .

Deadlock trong java?

DeadLock trong java là một trạng thái trong đó 2 hoặc nhiều thread rơi vào thực trạng chờ đón lẫn nhau vì mỗi thread giữ một tài nguyên và chờ đón tài nguyên từ thread khác. Ví dụ ThreadA giữ tài nguyên A và chời đợi tài nguyên B đang bị ThreadB nắm giữ, trong lúc đó ThreadB lại chờ đón ThreadA trả tài nguyên A để sử dụng dẫn đến ThreadA và ThreadB chờ đón lẫn nhau mãi mãi .

deadlock

Ví dụ
class TestThread {
public static Object Lock1 = new Object();
public static Object Lock2 = new Object();
public static void main(String args[]) {
ThreadDemo1 T1 = new ThreadDemo1();
ThreadDemo2 T2 = new ThreadDemo2();
T1.start();
T2.start();
}
private static class ThreadDemo1 extends Thread {
public void run() {
synchronized (Lock1) {
System.out.println(“Thread 1: Holding lock 1…”);
try { Thread.sleep(10); }
catch (InterruptedException e) {}
System.out.println(“Thread 1: Waiting for lock 2…”);
synchronized (Lock2) {
System.out.println(“Thread 1: Holding lock 1 & 2…”);
}
}
}
}
private static class ThreadDemo2 extends Thread {
public void run() {
synchronized (Lock2) {
System.out.println(“Thread 2: Holding lock 2…”);
try { Thread.sleep(10); }
catch (InterruptedException e) {}
System.out.println(“Thread 2: Waiting for lock 1…”);
synchronized (Lock1) {
System.out.println(“Thread 2: Holding lock 1 & 2…”);
}
}
}
}
}
Chúng ta có 2 thread ThreadDemo1 và ThreadDemo2, hai tài nguyên Lock1 và Lock2 .

  • Khi ThreadDemo1 start() nó bắt đầu chiếm giữ Lock1.
  • ThreadDemo1 ngủ 10millis, khoảng thời gian đó ThreadDemo2 start() và chiếm giữ lock2.
  • Sau khi ThreadDemo1 và ThreadDemo2 hoạt động, ThreadDemo1 giữ Lock1 và chờ ThreadDemo2 trả lại Lock2 để sử dụng.
  • ThreadDemo2 giữ Lock2 và đợi ThreadDemo1 trả lại Lock1

Dẫn đến ThreadDemo1 và ThreadDemo2 chờ lẫn nhau gây ra hiện tượng kỳ lạ Deadlock .
Để xử lý Deadlock ở ví dụ trên, mình sẽ sử dụng join ( ) method cho T1 để những những thread bên dưới phải chờ cho đến khi T1 thực thi xong thì mở màn khởi chạy .
class TestThread {
public static Object Lock1 = new Object();
public static Object Lock2 = new Object();
public static void main(String args[]) throws InterruptedException {
ThreadDemo1 T1 = new ThreadDemo1();
ThreadDemo2 T2 = new ThreadDemo2();
T1.start();
// waiting for T1 finished
T1.join();
T2.start();
}
private static class ThreadDemo1 extends Thread {
public void run() {
System.out.println(“Thread 1: Holding lock 1…”);
try {
Thread.sleep(10);
} catch (InterruptedException e) {
}
System.out.println(“Thread 1: Waiting for lock 2…”);
synchronized (Lock2) {
System.out.println(“Thread 1: Holding lock 1 & 2…”);
}
}
}
private static class ThreadDemo2 extends Thread {
public void run() {
System.out.println(“Thread 2: Holding lock 2…”);
try {
Thread.sleep(10);
} catch (InterruptedException e) {
}
System.out.println(“Thread 2: Waiting for lock 1…”);
System.out.println(“Thread 2: Holding lock 1 & 2…”);
}
}
}

Output :
Thread 1 : Holding lock 1 … Thread 1 : Waiting for lock 2 … Thread 1 : Holding lock 1 và 2 … Thread 2 : Holding lock 2 … Thread 2 : Waiting for lock 1 …Thread 2 : Holding lock 1 và 2 …

Cách tránh Deadlock

Để tránh Deadlock tất cả chúng ta phải biết đúng chuẩn những năng lực hoàn toàn có thể xảy ra Deadlock, việc này khá là khó khăn vất vả, mình chém gió vậy thôi chứ gặp Deadlock cũng đắm đuối. Thế nhưng mà tất cả chúng ta cứ nỗ lực thôi. Dưới đây là một số ít điểm tất cả chúng ta hoàn toàn có thể xem qua để giảm bớt năng lực Deadlock xảy ra

  • Cách đơn giản đã được mình nêu trên là sử dụng join() method để các thread khác chờ cho đến khi một thread hoàn thành mới bắt đầu khởi chạy. Lưu ý sử dụng khi nào cần thôi nhé, chứ bất đồng bộ mà cứ chờ nhau thì làm single thread cho rồi!
  • Tránh khoá các tài nguyên không cần thiết để hạn chế Deadlock, không phải cứ cái nào cũng khoá cho 1 thread, chúng ta phải xem xét kỹ xem tài nguyên đó có được sử dụng cho nhiều luồng và giá trị của nó có ảnh hưởng đến kết quả tính toán của các luồng hay không rồi hẳn khoá nhé.
  • Tránh việc khoá lồng nhau, khi một tài nguyên đã được giao cho 1 thread rồi thì đừng cố giao cho các thread khác. Đây là trường hợp phổ biến nhất dẫn đến DeadLock, như ví dụ trên Lock1 và Lock2 mình đã giao cho cả 2 thread chạy song song mà không có các biện pháp cụ thể khác.

Tóm lược

DeadLock là một yếu tố khó trong lập trình đa luồng, , mà tất cả chúng ta cần thực hành thực tế nhiều với đa luồng mới biết cách sử lý trong những trường hợp đơn cử. Deadlock cũng hoàn toàn có thể xảy ra những những truy vấn cơ sở tài liệu etc, nó hoàn toàn có thể xảy ra bất kể khi nào một tài nguyên được nhiều luồng giải quyết và xử lý tranh giành .
Deadlock hoàn toàn có thể phá huỷ luồng chạy thông thường của chương trình tại thời gian runtime, tác động ảnh hưởng nghiêm trọnåg đến thưởng thức người dùng .
Nguồn tìm hiểu thêm

https://www.geeksforgeeks.org/introduction-of-deadlock-in-operating-system/

https://www.tutorialspoint.com/java/java_thread_deadlock.htm Would love your thoughts, please comment. x

DeadLock là hiện tượng tranh chấp tài nguyên giữa hai hay nhiều lệnh trong đó lệnh này giữ tài nguyên mà lệnh kia cần dẫn tới việc không lệnh nào có thể kết thúc để giải phóng tài nguyên.
Ví dụ:

  • Giao dịch T1 giữ được tài nguyên R1, nhưng cần tài nguyên R2 để kết thúc và giải phóng R1
  • R2 lại đang bị T2 giữ và T2 cần R1 để kết thúc và sau đó giải phóng R2.
  • Trong trường hợp này cả T1 và T2 không thể kết thúc. Trường hợp này trong SQL Server sẽ phải chọn kill một trong hai giao dịch.

Xem thêm bài https://timoday.edu.vn/phan-tich-deadlock-trong-co-so-du-lieu-va-cach-phong-tranh/ Trong bài này chúng tôi ra mắt những cách khác nhau để tìm ra những lỗi DeadLock trong truy vấn cơ sở tài liệu của SQL Server

1. Sử dụng câu lệnh T-SQL SP_LOCK

Thực thi câu lệnh T-SQL SP_LOCK của SQL Server, bạn có thể tìm các status là WAIT cho các phiên đang bị chặn.

USE master;
GO
EXEC sp_lock;
GO
USE master ; GO EXEC sp_lock ; GO


Xem thêm tại đây

2. Sử dụng câu lệnh truy vấn với sys.sysprocesses

SELECT * FROM sys.sysprocesses
WHERE blocked > 0

3. Sử dụng trình DVM (Dynamic Management Views)

SELECT
der.blocking_session_id AS BlockingSessionID
,dest.text AS BlockingStatement
FROM sys.dm_exec_connections AS sdec
INNER JOIN sys.dm_exec_requests AS der
ON sdec.session_id = der.blocking_session_id
INNER JOIN sys.dm_os_waiting_tasks AS dowt
ON der.session_id = dowt.session_id
CROSS APPLY sys.dm_exec_sql_text(sdec.most_recent_sql_handle) AS dest

4. Sử dụng sys.dm_tran_locks

SELECT
request_session_id AS SPID
,DB_NAME(resource_database_id) AS DatabaseName
,resource_type AS LockedResource
,request_mode AS LockType
FROM sys.dm_tran_locks

5. Bật cờ theo dõi bắt buộc để ghi thông tin liên quan đến DeadLock trong Tracefile

DBCC TRACEON (1204, -1)
DBCC TRACEON (1222, -1)

6. Đếm tổng số lần xảy ra DeadLock

SELECT cntr_value AS TotalNumberOfDeadLocks
FROM sys.dm_os_performance_counters
WHERE counter_name = ‘Number of Deadlocks/sec’
AND instance_name = ‘_Total’

7. Sử dụng Extended Events và đoạn script bên dưới để tạo một Extended Event cho theo dõi DeadLock

CREATE EVENT SESSION [Deadlock_Monitor] ON SERVER
ADD EVENT sqlos.scheduler_monitor_deadlock_ring_buffer_recorded,
ADD EVENT sqlserver.lock_deadlock,
ADD EVENT sqlserver.lock_deadlock_chain,
ADD EVENT sqlserver.xml_deadlock_report
ADD TARGET package0.event_file(SET filename=N’C:\Temp\Deadlock_Monitor.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
SELECT * FROM sys.sysprocesses WHERE blocked > 0SELECT der. blocking_session_id AS BlockingSessionID, dest.text AS BlockingStatement FROM sys. dm_exec_connections AS sdec INNER JOIN sys. dm_exec_requests AS der ON sdec. session_id = der. blocking_session_id INNER JOIN sys. dm_os_waiting_tasks AS dowt ON der. session_id = dowt. session_id CROSS APPLY sys. dm_exec_sql_text ( sdec. most_recent_sql_handle ) AS destSELECT request_session_id AS SPID, DB_NAME ( resource_database_id ) AS DatabaseName, resource_type AS LockedResource, request_mode AS LockType FROM sys. dm_tran_locksDBCC TRACEON ( 1204, – 1 ) DBCC TRACEON ( 1222, – 1 ) SELECT cntr_value AS TotalNumberOfDeadLocks FROM sys. dm_os_performance_counters WHERE counter_name = ‘ Number of Deadlocks / sec ‘ AND instance_name = ‘ _Total ‘ CREATE EVENT SESSION [ Deadlock_Monitor ] ON SERVER ADD EVENT sqlos. scheduler_monitor_deadlock_ring_buffer_recorded, ADD EVENT sqlserver. lock_deadlock, ADD EVENT sqlserver. lock_deadlock_chain, ADD EVENT sqlserver. xml_deadlock_report ADD TARGET package0. event_file ( SET filename = N’C : \ Temp \ Deadlock_Monitor. 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

Bạn có thể sử dụng SSMS để tạo Extended Events cho DeadLock, và có thể theo dõi trạng thái trực tiếp của server.

Xem kết quả khi xảy ra DeadLock:

8. Sử dụng SQL Server Profiler

SQL Server Profiler có ba kiểu sự kiện khác nhau để bắt DeadLock :

  • Deadlock graph
  • Lock: Deadlock
  • Lock: Deadlock Chain
    Bước 1: Chọn Template là Blank

    Bước 2: Chọn kiểu Events là Locks để bắt các sự kiện liên quan đến DeadLock

Exit mobile version