Hitachi

OpenTP1 Version 7 分散トランザクション処理機能 OpenTP1 プログラム作成の手引


4.2.11 TAMのレコード追加・削除に伴う注意事項

排他確保によるデッドロックを発生させないためには,各UAPで確保する資源に対する排他の種類・順序を整理する必要があります。ここでは,TAMレコードの追加・削除に伴う排他確保によるデッドロックの発生と注意について説明します。

〈この項の構成〉

(1) トランザクションのデッドロック要因

(a) テーブル排他ありTAMテーブルアクセス機能を使用している場合

「追加削除できる更新型」のTAMテーブルで,同一トランザクション内で同一テーブルに対して「追加(削除),およびその他TAMアクセス」を行う場合は,このトランザクションがデッドロックの要因になる可能性があります。これは次の要因を満たす場合です。

  • 同一トランザクション内で同一テーブルに対して「追加(削除),およびその他TAMアクセス(排他あり)」を行う。

  • 「追加(削除),およびその他TAMアクセス」のアクセス順序が次のようになった場合

    「その他TAMアクセス」→「追加(削除)」

  • TAMテーブルのオープンが次のどちらかの場合

    • トランザクション外

    • トランザクション内でレコード排他(COBOL言語の場合はこのタイプ)

  • 上記トランザクションと同時に,排他確保の必要がある別トランザクションが同一テーブルにアクセスする。

(b) テーブル排他なしTAMテーブルアクセス機能を使用している場合

テーブル排他ありTAMテーブルアクセス機能でレコードを更新,追加,または削除していたTAMテーブルを,テーブル排他なしTAMテーブルアクセス機能を使用するように変更する場合,デッドロックとなることがあります。

テーブル排他ありTAMテーブルアクセス機能でレコードを更新,追加,または削除する場合,更新排他でテーブル排他を確保します。このため,追加または削除するレコードの順序が同じレコードにアクセスするほかのトランザクションと異なっていても,テーブル排他で待ち合わせているのでデッドロックにはなりません。しかし,テーブル排他なしTAMテーブルアクセス機能を使用するTAMテーブルではデッドロックとなることがあります。このため,テーブル排他ありTAMテーブルアクセス機能でレコードを更新,追加,または削除していたTAMテーブルを,テーブル排他なしTAMテーブルアクセス機能を使用するように変更する場合,UAPでアクセスするレコードの順序を統一してください。

テーブル排他ありTAMテーブルアクセス機能からテーブル排他なしTAMテーブルアクセス機能に変更してデッドロックとなる例を次の図に示します。

図4‒17 テーブル排他ありTAMテーブルアクセス機能からテーブル排他なしTAMテーブルアクセス機能に変更してデッドロックとなる例

[図データ]

UAP1では,レコード1,レコード3の順に削除し,UAP2では,レコード3,レコード1の順に更新するとします。テーブル排他ありTAMテーブルアクセス機能もテーブル排他なしTAMテーブルアクセス機能も図の(1)〜(4)の順に実行されるとします。

テーブル排他ありTAMテーブルアクセス機能では,次の手順で動作します。

  1. UAP1のレコード1の削除で,更新目的のテーブル排他を確保します。

  2. UAP2のレコード3の更新では,手順1と排他の競合が発生し,参照目的のテーブル排他の確保で排他解除待ちとなります。

  3. UAP1のレコード3の削除では,排他は確保しません。

  4. UAP1のトランザクションが決着することによって手順1で確保した排他が解放されると,手順2の排他解除待ちが解けてUAP2の処理が実行できます。

UAP1のトランザクションが決着したあと,UAP2の手順2では参照目的のテーブル排他と更新目的のレコード排他を確保し,手順4のレコード1の更新では,更新目的のレコード排他を確保します。

テーブル排他なしTAMテーブルアクセス機能では,次の手順で動作します。

  1. UAP1のレコード1の削除で,更新目的のレコード排他を確保します。

  2. UAP2のレコード3の更新で,更新目的のレコード排他を確保します。

  3. UAP1のレコード3の削除では,手順2と排他の競合が発生し,更新目的のレコード排他の確保で排他解除待ちとなります。

  4. UAP2のレコード1の更新では,手順1と排他の競合が発生し,更新目的のレコード排他の確保で排他解除待ちとなり,デッドロックが発生します。

デッドロックを回避するには,UAP1の手順1と手順3の順序を入れ替えるか,または,UAP2の手順2と手順4の順序を入れ替えます。

(2) 排他確保の流れ

同一トランザクション内で同一テーブルに対する排他確保の様子を,レコードの「更新+追加」という処理を例に説明します。

更新および追加の目的の排他確保の例を次の図に示します。

図4‒18 「更新+追加」の例

[図データ]

  1. 更新目的のdc_tam_writeで,この図の(1),(2)に示す排他を確保してレコードを更新します。

    目的のレコードは,「追加削除できる更新型」TAMテーブルにあります。このトランザクションが終了するまで,テーブル内のレコード構成を別トランザクションに変更させないために,テーブル全体に参照排他(PR)を確保します。

  2. 次に,追加目的のdc_tam_writeで,この図の(3)に示す排他を確保してレコードを追加します。

    テーブル内の構成を変更するので,このトランザクションが終了するまでテーブルを別トランザクションに参照させないために,テーブル全体に更新排他(EX)を確保します。

  3. 1.から2.の一連の処理の中で,テーブルに対する排他を「参照排他(PR)」から「更新排他(EX)」に変更しようとすることになります。

    1.から2.の処理の間で,デッドロックが発生する流れを次の図に示します。

    図4‒19 デッドロック発生

    [図データ]

    1.の処理のあとでかつ2.の処理が行われる前であれば,別トランザクションは同一テーブルに対してこの図の(2)-1に示すように参照排他(PR)を確保できます。このとき,別トランザクションが,本トランザクションで更新したレコードを排他確保しようとすると,テーブルに対して参照排他(PR)を確保したままレコードの排他解除待ちになります(この図の(2)-2)。

    その後,2.の処理が行われると,別トランザクションが同一テーブルに対して参照排他(PR)を確保しているために,テーブルに対して更新排他(EX)を確保できないで排他解除待ちになります。

  4. 3.によって,二つのトランザクションがお互いの排他資源の解除待ちになり,デッドロックとなります。

    この図では,自トランザクション内の追加の処理で必要になるはずの資源(テーブル)の更新排他(EX)を確保しないで処理(2.の手前までの処理)を進め,別トランザクションにテーブルの排他確保を許してしまったためにデッドロックとなりました。あらかじめテーブルに対して更新排他(EX)を確保していれば,別トランザクションにテーブルの排他を確保させることはありません。

    このため,同一トランザクション内では同一テーブルに対して「追加(削除)およびその他TAMアクセス」を行わないようにするなど,「(1) トランザクションのデッドロック要因」を満たさないようにしてください。

(3) デッドロックを避けるための注意

同一トランザクション内では同一テーブルに対して「追加(削除)およびその他TAMアクセス」を行う必要があり,上記のようなデッドロックの危険がある場合は,該当するトランザクションでテーブルに対して更新排他(EX)を確保してから処理をするようにしてください。

テーブルに対して更新排他を確保するためには,「追加(削除)」を先に行うか,またはC言語であればテーブルに対してトランザクション内でテーブル排他でオープンするようにしてください。