例:マクロを使用したヒープ破損の分離

この例では、プログラム例とヒープ破損を分離するために使用できる手法を示します。PL/I マクロ プリプロセッサと用意されているインクルード ファイルを使用します。

次の例で示す手法は、これまでに紹介した方法を使用してもメモリ破損の原因となっている場所を簡単に特定できない場合に特に役立ちます。

プログラム例 foo.pli

/* Example PL/I Program demonstrating a memory corruption 
    and the use of a macro to run down the point of failure.
    To compile: 
      mfplx -macro -incafter checkstomp.inc foo.pli 
 */

 foo: proc() options(main);

  dcl stompee1 char(10) based(stompptr);
  dcl stompee2 char(14) based(stompptr);
  dcl stompptr ptr;

  on error 
    begin;
      call PLIDUMP('FBCAT', 'Demo Memory Corruption');
    end;

  alloc stompee1; /* 10 bytes */
  stompee1 = '0123456789';  /* assign 10 bytes - happy happy */

  /* memory should be clean */
  $CHECKSTOMP();

  /* Create memory stomp and try again */
  stompee2 = 'ABCDEFGHIJKLMN'; /* pump in 14  and corrupt guard bytes */

  /* should be stomped! */
  $CHECKSTOMP();

 end foo;

このプログラム例では、$CHECKSTOMP(); を使用して、ヒープベースのメモリのメモリ ストンプを意図的に作成しています。コメント テキストで示してあるコマンド ラインを使用してコンパイルすると、破損が発生した文を分離するマクロ コードが生成されます。これには、SYSPRINT または CTF トレース (あるいはその両方) にメッセージを送るコードが含まれています。また、呼び出しスタックや変数の値などを示す PLIDUMP を生成する ERROR 条件も設定しています。

このプログラム例をコンパイルしてマクロ コードを生成するための推奨される手順を次に示します。

  1. checkstomp.inc インクルード ファイルを使用して foo.pli をコンパイルするように環境を設定します。checkstomp.inc は、バージョン 9.0 以降で %ProgramFiles(x86)%\Micro Focus\Enterprise Developer\include ディレクトリに用意されています。
    注: checkstomp.inc は、Enterprise Developer バージョン 6.0、7.0、および 8.0 と下位互換性があります。
  2. 次のコマンドを使用してコンパイルします。
    mfplx -macro -incafter checkstomp.inc -pp
    foo.pp foo.pli

    foo.pp は、マクロで生成されたコードを格納する中間出力ファイルです。

マクロによる処理の内容をしっかりと理解できるまで、マクロで生成されたコードを確認することを強くお勧めします。内容が理解できたら、この手法を独自の PL/I プログラムに適用して破損が発生した文を特定できます。

  1. この例で示しているように、プログラム コード内の戦略的なポイントに $CHECKSTOMP(); の呼び出しを追加します。
  2. 次のようにプログラムをコンパイルします。
    mfplx -macro -incafter checkstomp.inc -pp
    prog-name.pp prog-name.pli
  3. プログラムを実行します。
  4. SYSPRINT、CTF トレース、および PLIDUMP の出力と、プログラムによって生成されたその他の情報を確認します。

サンプル セッション:

c:\work\emergency\jan13
ED>mfplx -macro -incafter checkstomp.inc -pp foo.pp foo.pli

c:\work\emergency\jan13
ED>foo

Memory Clean: FOO Line #(22)
Memory Corruption detected: FOO Line #(28)