V3R2M0 からのBIFFコードとしてプロシージャーのポインターを示す %PADDR
があるが
どのような使用目的があるのかが、よくわからない人も多いと思われる。
直接、プロシージャーを呼べばよいものを、何故ポインターを指定する必要があるのかが
明確でないのかも知れない。
%PADDR
を使用する目的は不明な汎用的なプロシージャーの実行を可能にすることである。
例えばある親プログラムから子の *SRVPGM
を呼び出すことを想定しよう。
PGMA
はデータ・ベース MYFILE をアクセスして一覧表を印刷する。
PGMB
はデータ・ベース MYFILE をアクセスして画面に表示する。
そこでデータ・ベースをアクセスする部分は共通しているので、ひとつの *SRVPGM
に
まとめるものとする。処理は次のようになる。
PGMA
から開始 »
SRVPGMA
で MYFILE をアクセス »
PGMA
に戻って一覧表を印刷
PGMB
から開始 »
SRVPGMA
で MYFILE をアクセス »
PGMB
に戻って画面表示
いずれの場合も MYFILE をアクセスする SRVPGMA
にキーなどのレコードを取得するための
情報を渡すことになるが、同時に次の処理としての「一覧表印刷」や「画面表示」の処理だけ
をプロシージャーとして定義しておいて、SRVPGMA
にプロシージャーのポインターを渡してやり、
PGMA や PGMB に戻ってからプロシージャーを実行するのではなくSRVPGMA
の中で
親プログラムのプロシージャーを呼び出すように記述することができる。
つまり SRVPGMA
のプロシージャーを呼び出すときに
CALLP CHILD(SHCODE:%PADDR('MYPRINT')
のようにして親PGM の MYPRINT
というプロシージャーのポインターも渡してやる。
子*SRVPGM では MYFILE を SHOCDE を使ってアクセスした後で
CALLB PROC
のようにして、親PGM のプロシージャーを子自身が実行することができるのである。
さて、このような処理にどのような利点があるのであろう?
読者は処理を複雑にしているだけのように思われるかも知れない。
この処理の意味は MVS である処理の分離である。
親PGM はユーザー・インター・フェースの部分しか行っていない。
これに対して子SRVPGM はデータ・アクセスの部分しか行っていない。
さらにはプロシージャーを直接、呼ぶよりは繰り返し処理となるとポインタによる操作のほうが
パフォーマンスが向上する利点もある。
不明な名前のプロシージャーを動的に実行できる汎用性を備えたいのであれば%PADDR
の
使用が必要となる。