こんにちは!メインフレームの世界へようこそ。
JavaやCOBOLといったモダン、あるいは少し前の業務系言語をバリバリ書いてきた方にとって、IBMメインフレームの「PL/I(ピーエルアイ)」、そしてオンライン制御プログラムである「CICS(シーアイシーエス)」の組み合わせは、最初に目にしたとき少し奇妙に映るかもしれませんよね。
「なんだこの暗号みたいなコードは……」と、黒い画面(3270エミュレータ)の前で冷や汗をかいた方もご安心ください。怖がる必要は全くありません。ボンネットの中身を一つずつ覗いていけば、「なるほど、こうなっているのか!」と納得できる合理的な仕組みが見えてきますよ。
今回は、CICS環境で動くPL/Iプログラムの心臓部、「`EXEC CICS`コマンドが裏側でどう料理されて実行されているのか」という秘密のプロセスを、優しく紐解いていきましょう。
—
1. COBOLとは一味違う? PL/Iの「予約語を持たない」世界観
JavaやCOBOLには、変数名に使ってはいけない「予約語(`IF`, `MOVE`, `DISPLAY` など)」が厳格に決まっていますよね。しかし、PL/Iの非常にユニークな(そして初学者が戸惑う)特徴の一つに、「言語としての厳密な予約語を持たない」という仕様があります。
たとえば、COBOLなら絶対に変数名に使えないような単語であっても、PL/Iでは文脈から判断されるため、極端な話、コンパイラが「あ、ここは変数だな」と理解できればエラーになりません。
ただ、CICSと組み合わせて使うときには、この自由度の高さが逆に「おや?」と思わせるポイントになります。CICSの命令である `EXEC CICS` は、PL/I本来の構文ではなく、IBMが提供するプリコンパイラ(翻訳前の下準備をしてくれるツール)によって独自の変換を受けるからです。
—
2. 魔法の翻訳機:DFHECP1によるプリコンパイルの裏側
私たちが普段、オンライン画面を制御するために書くコードは、このような形をしていますよね。
1
/ 画面にメッセージを送信するCICSコマンドの例 /
EXEC CICS SEND MAP(‘MENUMAP’)
MAPSET(‘MENUSET’)
DATAONLY;
JavaやCOBOLしか触ったことがない方なら、「お、これがCICSの命令文だな」と直感的に分かります。しかし、実はこの `EXEC CICS` という記述、そのままではPL/Iのコンパイラは理解できません。
そこで登場するのが、CICSのプリコンパイルプログラムである `DFHECP1`(通称:CICSトランスレータ) です。
コンパイルの直前にこの `DFHECP1` がソースコードをスキャンし、私たちが書いたお洒落な `EXEC CICS` を、PL/Iがガチガチに理解できる「サブルーチンへのCALL文」へとごっそり書き換えてしまうのです。
人間で例えるなら、外国語(CICS語)で書かれた手紙を、秘書(DFHECP1)がその場でPL/Iがペラペラ喋れる日本語(CALL文)に全訳してくれるようなイメージですね。
—
3. 展開された「CALL文」と伝説のインターフェース領域(DFHEIVAR)
では、実際に `DFHECP1` が裏側でどんなコードを生成しているのか、その姿を見てみましょう。先ほどの `SEND MAP` コマンドは、プリコンパイルを通すと、だいたい次のようなPL/Iのコードに生まれ変わります。
1
/ —————————————————————- /
/ DFHECP1によって自動展開されたコードのイメージ /
/ —————————————————————- /
DCL DFHEIVAR ENTRY EXTERNAL; / CICS共通インターフェースへのエントリ /
/ 各種パラメータをセットしてCICSの頭脳へバトンタッチする /
CALL DFHEIVAR (
X’02040000′ , / ファンクションコード(どの命令を実行するか) /
DFHRESP(NORMAL), / 応答コードなどを格納するエリア /
MENUMAP , / マップ名 /
MENUSET / マップセット名 /
);
ここで登場するのが、今回のテーマの主役の一つである `DFHEIVAR` です。
`DFHEIVAR` は、CICS環境と私たちのPL/Iプログラムをつなぐ「専用の連絡通路(インターフェース領域)」のようなものです。
`EXEC CICS` コマンドに渡したオプション(画面の名前や、データを送る・受け取るなどの指示)は、すべてこの `DFHEIVAR` を経由してCICSの心臓部(DFHIPモジュールなど)へと届けられます。
変数名のような、コマンドのような……「DFH」で始まる仲間たち
コードを書いていると、`DFHRESP` や `DFHCOMWA` など、「DFH」から始まる見慣れない単語によく出会います。これらはCICSが提供するマクロや組み込み関数であり、PL/Iのデータ構造(ストラクチャー)や定数としてあらかじめ定義されています。
レガシーなシステムでは、こうした「DFH」から始まる固有のお作法がたくさんありますが、恐れることはありません。要は「CICS様と会話するための共通言語(方言)」だと思えば、すんなり頭に入ってくるはずです。
—
4. 実務で役立つ! CICS + PL/Iプログラムの全体像
最後に、CICSの通信領域(COMMAREA)を受け取り、画面に挨拶を返すだけのシンプルなオンライン・プログラムの全体像を見てみましょう。Javaのサーブレットや、COBOLのCICSプログラムと見比べてみてください。
1
/==================================================================/
/ プログラム名: HELLOAPP /
/ 概要 : CICS環境で動く基本的なPL/Iオンラインプログラム /
/==================================================================/
HELLOAPP: PROC OPTIONS(MAIN, CICS);
/ 1. 通信領域(COMMAREA)の定義 /
DCL 1 CICS_COMMAREA,
5 氏名 CHAR(20),
5 メッセージ CHAR(40);
/ 2. CICSからの呼び出しに対する初期処理(ADDRESS COMMAREA) /
EXEC CICS ADDRESS COMMAREA(Ptr_Commarea);
/ 3. 画面からの入力や、ビジネスロジックの処理(今回は省略) /
/ 4. SENDコマンドによる画面出力(裏でDFHEIVARに変換されます!) /
EXEC CICS SEND TEXT
FROM(CICS_COMMAREA)
ERASE;
/ 5. 処理の正常終了をCICSに通知してリターン /
EXEC CICS RETURN;
END HELLOAPP;
このように、`PROC OPTIONS(MAIN, CICS);` と宣言することで、このプログラムが単なるバッチではなく「CICSのオンラインプログラムとして動くんだよ」とコンパイラとCICSに教えてあげることができます。
—
まとめ:怖がらなくて大丈夫、仕組みはとてもシンプルです!
いかがでしたでしょうか?
「PL/Iの構文規則」や「`EXEC CICS` の裏側での変換(DFHECP1とDFHEIVAR)」と言われると、なんだか難しそうな呪文のように感じてしまいますよね。
でも、中身を紐解いてみれば、
1. 私たちが書いた `EXEC CICS` を、
2. 翻訳機(`DFHECP1`)が、
3. お馴染みの `CALL DFHEIVAR` に書き換えて、
4. CICSと安全にデータやり取りをしている。
これだけのシンプルな仕組みです。
他言語の経験があるあなたなら、データ構造や制御フローの概念はすでにバッチリ持っているはずです。レガシー特有の作法に出会っても、「あ、裏ではこういう通訳をしているんだな」とイメージできれば、もう怖くありません。
ぜひ自信を持って、メインフレームの世界へ一歩を踏み出してくださいね!あなたのスキルアップを心から応援しています。
