取り消し処理プログラムの使用

取り消し処理プログラムは、呼び出しスタック項目が通常の戻り以外の何らかの理 由によって打ち切られた時に、終結処置および回復処置のための制御を受け取 れるようにするという重要な機能を提供します。 例えば、プロシージャーがシステム要求 '2' によって、あるいは 照会メッセージに 'C' (取り消し) の応答があったために終了した時に、 制御を受け取るために取り消し処理プログラムを必要とする場合があります。

呼び出しスタック項目終了ユーザー出口プロシージャー登録 (CEERTX) および、 呼び出しスタック項目終了ユーザー出口プロシージャー (CEEUTX) ILE バインド可能 API は、 ユーザー定義ルーチンが登録される呼び出しスタック項目が取り消された時に実行する、このユーザー定義 ルーチンを自動的に登録する方法を提供します。 登録されると、呼び出しスタック項目が除去されるか、 あるいは CEEUTX が使用禁止にするために呼び出されるまで、取り消し処理プログラムは有効のままとな っています。 ILE バインド可能 API についての詳細は、Web サイト http://www.ibm.com/eserver/iseries/infocenteriSeries Information Center の中の『プログラミング』カテゴリーの『CL および API』の節を参照してください。

図 139 は、サブプロシージャーの取り消し処理プログラムの 活動可能化、およびコーディングの例を示します (また、取り消し処理プログラムは 同じ方法でメイン・プロシージャーを使用可能にすることができます)。

図 139. サブプロシージャーの取り消し処理プログラムの活動可能化、および コーディング
      *-----------------------------------------------------------------
      * 取り消し処理プログラムのプロトタイプを定義します。
      * このプロシージャーはローカル・プロシージャーです。
      *-----------------------------------------------------------------
     D CanHdlr         PR
     D   pMsg                          *
      *-----------------------------------------------------------------
      * 取り消し処理プログラムを使用可能にするための
      * サブプロシージャーのプロトタイプを定義します。
      *-----------------------------------------------------------------
     D Enabler         PR
      *-----------------------------------------------------------------
      * Enabler を呼び出すためのサブプロシージャーのプロトタイプを
      * 定義します。
      *-----------------------------------------------------------------
     D SubProc         PR
      *-----------------------------------------------------------------
      * メイン・プロシージャー。SubProc を 3 回呼び出します。
      *-----------------------------------------------------------------
     C                   CALLP     SubProc
     C                   CALLP     SubProc
     C                   CALLP     SubProc
     C                   SETON                                        LR
      *-----------------------------------------------------------------
      * プロシージャー SubProc。Enabler を呼び出します。この呼び出しは
      * 失敗することになるので、エラーを処理するローカル *PSSR サブ
      * ルーチンを定義します。
      *-----------------------------------------------------------------
     P SubProc         B
     C                   CALLP     Enabler
      *-----------------------------------------------------------------
      * PSSR に RETURN 命令があるため、メイン・プロシージャーからの
      * SubProc に対する呼び出しは失敗します。
      *-----------------------------------------------------------------
     C     *PSSR         BEGSR
     C     'Subproc PSSR'DSPLY
     C                   RETURN
     C                   ENDSR
     P SubProc         E
      *-----------------------------------------------------------------
      * プロシージャー Enabler。このプロシージャーは取り消し処理
      * プログラムを使用可能にしてから、Enabler が取り消される原因
      * となるエラーを受け取ります。
      *-----------------------------------------------------------------
     P Enabler         B
      * ローカル変数
     D Handler         S               *   PROCPTR  INZ(%PADDR('CANHDLR'))
     D Msg             S             20A
     D pMsg            S               *   INZ(%ADDR(Msg))
     D Zero            S              5P 0 INZ(0)
     D Count           S              5I 0 INZ(0) STATIC
     D Array           S              1A   DIM(2)
      *-----------------------------------------------------------------
      * 取り消し処理プログラムを使用可能にします。このプロシージャーが
      * 取り消された時にプロシージャー 'CANHDLR' が呼び出されます。
      *-----------------------------------------------------------------
     C                   CALLB     'CEERTX'
     C                   PARM                    Handler
     C                   PARM                    pMsg
     C                   PARM                    *OMIT
      *-----------------------------------------------------------------
      * このプロシージャーは 3 回呼び出されます。最初の 2 回は、取り消し
      * 処理プログラムが使用可能になった時にエラーを受け取ります。
      *-----------------------------------------------------------------
     C                   EVAL      Count = Count + 1
     C                   SELECT
     C                   WHEN      Count = 1
     C                   EVAL      Msg = 'Divide by zero'
     C                   EVAL      Zero = Zero / Zero
     C                   WHEN      Count = 2
     C                   EVAL      Msg = 'String error'
     C     'A'           SCAN      'ABC':Zero    Zero
      *-----------------------------------------------------------------
      * 3 回目の呼び出しでは取り消し処理プログラムが使用不可にされます。
      * 配列指標エラーのためにプロシージャーは失敗しますが、
      * 処理プログラムは呼び出されません。
      *-----------------------------------------------------------------
     C                   WHEN      Count = 3
     C                   CALLB     'CEEUTX'
     C                   PARM                    Handler
     C                   PARM                    *OMIT
     C                   EVAL      Msg = 'Array index error'
     C                   EVAL      Array(Zero) = 'x'
     C                   ENDSL
     P Enabler         E
      *-----------------------------------------------------------------
      * 取り消し処理プログラムを定義します。パラメーターは、表示される
      * メッセージを示す「連絡域」へのポインターです。
      *-----------------------------------------------------------------
     P CanHdlr         B
     D CanHdlr         PI
     D   pMsg                          *
      *-----------------------------------------------------------------
      * 入力ポインター pMsg に基づいてフィールドを定義します。
      *-----------------------------------------------------------------
     D Msg             S             20A         BASED(pMsg)
      *-----------------------------------------------------------------
      * 処理プログラムを使用可能にしたプロシージャーが設定した
      * メッセージを表示します。
      *-----------------------------------------------------------------
     C     'Cancel Hdlr 'DSPLY                   Msg
     P CanHdlr         E

次は、プログラム CANHDLR からの出力を示しています。 プロシージャー SubProc の *PSSR が 3 回呼び出されて いますが、3 番目のエラーの前に使用不可になったために、取り消し処理プログラムは 2 回だけ 呼び出されています。

図 140. CANHDLR プログラムからの出力
DSPLY  Cancel Hdlr     ゼロによる除算
DSPLY  Subproc PSSR
DSPLY  Cancel Hdlr     ストリング・エラー
DSPLY  Subproc PSSR
DSPLY  Subproc PSSR