問題タブ [deadlock]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
sql-server - SQLServer2000のデッドロック
本番SQLServer2000データベースで、非常に厄介なデッドロック状態が発生しています。
主な設定は次のとおりです。
- SQL Server2000EnterpriseEdition。
- サーバーは、ATLOLEデータベースを使用してC++でコーディングされています。
- すべてのデータベースオブジェクトは、ストアドプロシージャを介してアクセスされています。
- すべてのUPDATE/INSERTストアドプロシージャは、内部操作をBEGIN TRANS ...COMMITTRANSブロックでラップします。
このようなインターネット上のいくつかの記事に従って、SQL Profilerを使用していくつかの初期トレースを収集しました(SQL Server 2005ツールを参照していることを無視してください。同じ原則が適用されます)。トレースから、2つのUPDATEクエリ間のデッドロックのように見えます。
問題が発生する可能性を減らすために、次のような対策を講じています。
- SELECT WITH(NOLOCK)。ストアドプロシージャのすべてのSELECTクエリをWITH(NOLOCK)を使用するように変更しました。ダーティリードの影響は理解していますが、多くの自動更新を実行し、通常の状態ではUIに適切な値が設定されるため、クエリ対象のデータはそれほど重要ではありません。
- コミットされていないを読んでください。サーバーコードのトランザクション分離レベルをREADUNCOMMITEDに変更しました。
- トランザクションスコープの縮小。データベースのデッドロックが発生する可能性を最小限に抑えるために、トランザクションの保持時間を短縮しました。
また、ストアドプロシージャの大部分(BEGIN TRANS ... COMMIT TRANSブロック)内にトランザクションがあるという事実にも疑問を投げかけています。この状況では、トランザクション分離レベルはシリアライズ可能だと思いますよね?また、ストアドプロシージャを呼び出すソースコードでトランザクション分離レベルも指定されている場合はどうでしょうか。どちらが適用されますか?
これは処理集約型のアプリケーションであり、読み取り(より大きな割合)と一部の書き込みでデータベースに多くの影響を与えています。
これがSQLServer2005データベースの場合、スタックオーバーフローに関するデッドロックの問題について、Geoff Dalgasの回答を使用できます。これが、発生している問題にも当てはまります。ただし、現時点では、SQLServer2005へのアップグレードは実行可能なオプションではありません。
これらの最初の試みが失敗したので、私の質問は次のとおりです。ここからどのように進みますか?デッドロックの発生を減らす、または回避するためにどのような手順を実行しますか、または問題をより適切に明らかにするためにどのコマンド/ツールを使用する必要がありますか?
python - この MySQLdb のバグを誰も気にしないのはなぜですか? バグですか?
TL;DR: 見つかったバグのパッチを提供しましたが、フィードバックはありません。それがバグなのかどうか疑問に思っています。これは暴言ではありません。これを読んで、影響を受ける可能性がある場合は、修正を確認してください。
私は数週間前にこの MySQLdb バグを発見して報告し (編集: 6 週間前)、パッチを送信し、ORM のいくつかのフォーラムに投稿し、MySQLdb の作成者にメールを送り、デッドロックの処理について話している人にメールを送り、ORM の作成者にメールを送りました。どんな種類のフィードバックも待っています。
このバグは私に多くの悲しみをもたらしました.フィードバックで見つけることができる唯一の説明は、mysqlでPythonで「SELECT ... FOR UPDATE」を使用する人がいないか、これはバグではないということです.
基本的に問題は、MySQLdb カーソルを使用して「SELECT ... FOR UPDATE」を発行するときに、デッドロックと「ロック待機タイムアウト」例外が発生しないことです。代わりに、ステートメントは暗黙のうちに失敗し、空の結果セットを返します。これは、アプリケーションが一致する行がなかったかのように解釈します。
SVN バージョンをテストしましたが、まだ影響を受けています。Ubuntu Intrepid、Jaunty、および Debian Lenny のデフォルト インストールでテストされ、それらも影響を受けます。easy_install (1.2.3c1) によってインストールされた現在のバージョンが影響を受けます。
これは SQLAlchemy と SQLObject にも影響し、おそらく MySQLdb カーソルを使用するすべての ORM も影響を受けます。
このスクリプトは、バグを引き起こすデッドロックを再現できます (get_conn でユーザー/パスを変更するだけで、必要なテーブルが作成されます)。
パッチが適用されていない MySQLdb でこれを実行した場合の出力は次のとおりです。
Thread-2 がテーブルから 0 行を取得したことがわかります。1 行あることがわかっており、"SHOW WARNINGS" ステートメントを発行するだけで、何が起こったかを確認できます。「SHOW ENGINE INNODB STATUS」をチェックすると、ログに「*** WE ROLL BACK TRANSACTION (2)」という行が表示されます。Thread-2 で選択に失敗した後に発生するすべてのことは、半分ロールバックされたトランザクションにあります。
パッチを適用した後 (以下の URL のチケットを確認してください)、これはスクリプトを実行した結果です。
この場合、Thread-2 で例外が発生し、適切にロールバックされます。
それで、あなたの意見はどうですか?、これはバグですか? 誰も気にしませんか、それとも私はただクレイジーですか?
これは私が SF で開いたチケットです: http://sourceforge.net/tracker/index.php?func=detail&aid=2776267&group_id=22307&atid=374932
sql-server-2008 - SELECT/UPDATE でのデッドロック
SQL Server 2008 で SELECT/UPDATE のデッドロックに問題があります。このスレッドからの回答を読みました: SQL Server は選択/更新または複数の選択の間でデッドロックしますが、デッドロックが発生する理由はまだわかりません。
次のテストケースで状況を再現しました。
私はテーブルを持っています:
最初にこのテーブルからレコードを選択しようとしています。レコードが存在する場合は、有効期限を現在の時刻に間隔を加えたものに設定します。次のコードを使用して実現します。
次に、2 つのスレッドからテスト メソッドを実行しようとして、それらが同じレコードを更新しようとすると、次の出力が得られます。
Serializable Isolation Level を使用してどのように発生するのか理解できません。最初の選択で行/テーブルをロックする必要があり、別の選択でロックを取得できないと思います。この例はコマンド オブジェクトを使用して記述されていますが、これは単なるテスト用です。元々、私はlinqを使用していますが、単純化された例を示したかったのです。Sql Server Profiler は、デッドロックがキー ロックであることを示しています。数分で質問を更新し、SQL サーバー プロファイラーからグラフを投稿します。どんな助けでも大歓迎です。この問題の解決策は、コード内にクリティカル セクションを作成することである可能性があることは理解していますが、Serializable Isolation Level でうまくいかない理由を理解しようとしています。
そして、これがデッドロック グラフです: デッドロック http://img7.imageshack.us/img7/9970/deadlock.gif
前もって感謝します。
sql-server - MS SQL Serverの追加専用テーブルのロックを最小限に抑えるためのアドバイスはありますか?
(エラーがスローされたときや開発中だけでなく)本番環境で実行されるロギング/監査コードを書いています。Coding Horrorのデッドロックとロギングの経験を読んだ後、私はアドバイスを求めるべきだと決めました。(「ログに記録しない」というJeffのソリューションは私には機能しません。これは、法的に義務付けられているセキュリティ監査です)
競合とデッドロックを最小限に抑えるための適切な分離レベルはありますか?挿入ステートメントまたはストアドプロシージャに追加できるクエリヒントはありますか?
私は、監査テーブルを除くすべてのトランザクションの整合性に深く関心を持っています。非常に多くのログが記録されるため、いくつかのエントリが失敗しても問題はありません。ロギングが他のトランザクションを停止した場合、それは悪いことです。
データベースまたはファイルにログを記録できますが、ファイルへのログ記録は、結果を何らかの方法で表示できる必要があるため、あまり魅力的ではありません。ただし、ファイルにログを記録すると、ログが他のコードに干渉しないことが(ほぼ)保証されます。
c# - 次の SQL Server がトランザクション内で実行されると、デッドロックが挿入されるのはなぜですか?
現在、SQL Server テーブルにレコードを挿入し、次のように自動インクリメント ID を選択しています。
(これは Linq-to-SQL を使用して生成されました)。Serializable 分離レベルで TransactionScope オブジェクトを使用してトランザクション内でこのコードを実行すると、何らかの理由で SQL Server がデッドロック エラーをスローします。デッドロック グラフ イベントを分析したところ、関連する 2 つのプロセスがそれぞれ、変換操作を実行するために相互に待機していることがわかりました。次の情報を理解しているためです。
私の理解では、トランザクション スコープは、最初のプロセスが ID の挿入と選択の両方を完了するまで、2 番目のプロセスが挿入を実行できないようにするというものでした。しかし、そうではないようです。スレッドセーフな方法で私が必要とするものを達成するための最良のアプローチに誰かが光を当てることができますか?
--更新--
注意してください。それぞれがデータベースと通信するための新しい DataContext を作成するため、2 つのプロセス間で接続が共有されていないことは 99% 確信しています。
--再度更新--
Remus Rusanu は、いくつかの省略された情報が問題に関連していることを指摘しました。デッドロック グラフ レポートに基づいてシナリオを単純化しようとしましたが、ここで説明を拡張しました。挿入を行う前に、問題のテーブルに対して既存のクエリを実行して、タグが既に存在するかどうかを確認します。もしそうなら、私は取引を終了します。Some_Int
そうでない場合は、挿入を続行する必要があります。次に、更新は純粋に最後に変更された値に対するものですが、ここには示されていませんが、主キーを持つテーブルで更新を実行します。Tag テーブルに、auto inc ID と Some_Int の両方で構成されるクラスター化インデックスがあることも重要な場合があります。この最後の情報は関連性があるとは思いませんでした。主キー/クラスター化インデックスとして auto inc フィールドのみを持つようにテーブルを変更しようとしても役に立たなかったからです。
ありがとう。
multithreading - MT プログラムでデッドロック スレッドをデバッグしますか?
gdb 以外の MT プログラムでデッドロック スレッドをデバッグする方法は何ですか?
multithreading - マルチスレッドプロセスでのデッドロックを回避する
デッドロックを回避するために誰かが従うべきベストプラクティス/イディオムは何ですか?
java - select()が呼び出されている間、セレクターにチャネルを登録している間、Javaスレッドはブロックします。何をすべきか?
基本的な質問があります。SelectableChannelのregisterメソッドが呼び出しをブロックする理由と方法。シナリオを提供させてください。
次のように、RegisterクラスにSelectorオブジェクトを作成しました。
同じクラス(Register)にチャンネルをセレクターに登録するメソッドもあります。
また、Requestという名前の別のクラスがあります。このクラスには、チャネルからデータを読み取り、処理し、次のメソッドを呼び出してチャネルを登録するメソッドがあります。
ここで、この時点でスレッドはブロックされ、何を待っているのかがわかりません。セレクターが開いていることを確認しました。これを解決する方法を理解するために、私にいくつかの助けを提供してください。解除できるロックはありますか?
任意の入力をいただければ幸いです。
私が説明したことに加えて。さらにテストを行ったところ、Register.registerメソッドが同じスレッドから呼び出された場合は登録できますが、その後、他のスレッドがメソッドを呼び出そうとしても、スレッドは先に進みません。