モードにも対応することにした。見栄えの 話をするならば , 明らかにノーマルモード よりもハイレゾリューションモードのほう が優れている。また , 実用性の面からも , ハイレゾリューションモードのテキスト 31 行表示に関しては , 一度に確認て、きる情報 量が増えるという点て、有利て、ある。モード 内部構造はノーマルモードとにているし , 幅広い機種のサポートは決してユーザの不 利益にはならないて、あろうから , 対応を決 定した。実際には , ノーマルモードとハイ レゾリューションモードとの非互換性は , Turbo C 十十だけて、なく , Turb0 Debug ger, Turbo profiler の移植担当者を最後ま て、悩ませることにもなったが , それだけの 価値があったと信じている。 工テイタ 統合環境のエデイタは , 移植担当者が苦 労した点のひとって、ある。従来の Turbo シリ ーズのエデイタて、は , 一度にひとつのファ イルだけしか編集て、きず , MS-DOS のメイ ンメモリからエディットバッフアを確保す るだけて、サイズも 64K バイトに制限されてい た。また , 日本語版て、はスクロール速度が 遅いなどの不満も聞かれた。 TurboC 十十て、は , これらの点がすべて 改善されている。 Turbo C 十十のエデイタ は , 合計 8M バイトまて、の複数のファイルを 編集することがて、きる。また , キャッシュ 機能が組み込まれており , どんなに大きな ファイルて、も ( オープンするときに時間がか かるだけて、 ) 任意の場所へ瞬時に移動するこ とがて、きる。このキャッシュ機能のために ファイルの内容が単純にメモリ上に存在す るわけて、はないため , 漢字 ( 2 バイト系文字 ) の取り扱いに苦労したようて、ある ( 残念なが ら , NEC 独自の 2 バイト系半角文字には対応 てきなかった ) 。 また , 画面のスクロールなどの表示速度 に関しても基本的な見直しを行い , 大幅に 改善された。 60 CMAGAZINE 1991 2 日本語化において , もうひとつ追加され たのが , 文字列検索において全角 , 半角文 字を同一視する機能て、ある。プログラム中 のコメントに出てくる英文を全角て、記述し たり , 半角て、記述したりしてしまうことが ある。このとき , いちいち両方の検索文字 列て、検索を行わなければならないのは不便 て、ある。もちろん , どちらかに統一して記 述しておけばよいのだが , 他人が記述した プログラムを参照したりする場合もあるだ ろうから , そうした場合には便利て、あろう。 また , TurboC 十十に組み込まれているプ ロジェクト機能には , Projectnotes という プログラム開発上のコメントを記述するウ こて、利用 インドウも用意されているが , することもて、きる。ただし , この機能て、同 一視て、きるのは英数字のみて、ある。 一般に , Turbo C 十十の内蔵工デイタを 始めとする IBM ー PC 系のエデイタは , 日本 のエデイタのように画面の右端て、折り返す 機能をもたないため , 日本語文章の編集に は向いていないが , プログラムをコーディ ングするには十分実用的になったといえる て、あろう。むしろ , キャッシュ機能 , オー バーラッブマルチウインドウ , マウスのサ ポートなどを考慮すれば , プログラム開発 においては , ほかのエデイタを上回ってい るといっても過言て、はないだろう。 拡張メモリの対応 NEC が , グラフィックス VRAM と EMSAZ ージを同じ領域に割り当ててしまったのは , ソフトウェア開発者の苦労のタネを増やし たようなものて、ある。たとえば , Turbo C 十十 の統合環境のように , EMS を扱うアプリケ ーションから , BGI のようなグラフィックス を扱うプログラムをデバッグするときなど は , ややこしい問題を招く。 一時は , 対応を諦めたほうがよいのて、は ないかという意見も出たが , 実際にこの形 式の EMS ドライバを使っているユーザも少 なくないようなのて、 , 結局対応することに したにれもまた , 移植担当者を悩ませた ) 。 プロテクトモード用の拡張メモリについ ても同様て、ある。 IBM-PC 版て、は , プロテ クトモード用の拡張メモリを使うために XMS ドライバが使われているが , PC ー 9801 用の XMS ドライバとは HMA という拡張メモリ の最初の 64K バイトの領域だけをサポートし ているサプセットがほとんどて、ある。 しかし , TurboC 十十が使用するのは EMB という拡張メモリ全体を指すプロックて、あ したがって , そのままて、は Turbo C 十十か ら使うことがて、きない。しかし , フルセッ トの XMS ドライバがないからといってプロ テクトモード用の拡張メモリが使えないと いうのて、は意味がない 統合環境は , 当然機種に依存するものだ から , PCー9801 版 Turbo C 十十て、は XMS ド ライバを使わずに共通アドレスの [ 0000 : 0401 ] を参照することて、拡張メモリの大き さを取得するようにし , INTI 価を使ってプ ロテクトモード用メモリの転送を行ってい る。なお , 共通アドレスの値は , 一部の EPSON マシンて、は設定されていないことがあるよ うて、 , この値を設定するためのツールもサ ポートすることになった。 こて、問題になるのが , コマンドライン コンパイラて、ある。 TurboCVer. 2.0 のコ マンドラインコンパイラが機種依存してい る点については , 多くのユーザの方から批 判を受けたし , 私たちとしても余計な機種 依存性は排除したいと考えていた。しかし , ー Qe オプション (EMS メモリの利用 ) やー Qx オ プション ( プロテクトモード用拡張メモリの 利用 ) を PC ー 9801 専用にしてしまうと , 他機 種て、これらのオプションを使えない なってしまう。コマンドラインコンパイラ の一 Qe オプションは NEC ー EMS に対応してい るが , NEC-EMS 独自のファンクションて、 工ラーが発生しても無視する ( この場合は NEC-EMS て、ないとみなす ) 。ー Qx オプショ ンを使うためには , XMS ドライバが必須と なっている。
耳むずかしながらドジりました 3 ~ 4 年ぐらい前 , アメリカのパソコンプ ログラミング雑誌界ては , 「 TSR プログラム を自作しよう」というテーマが , 5 本の指に 入るぐらいの大きな話題になっていました。 OOP も GUI もほとんどまだ誌上には登場し ない , 思えば平和な ( ? ) 時代てした。 TSR とは , Terminate and Stay Residend の頭文字て , 訳すと「終了常駐」とてもなり ますか。 MS ー DOS 上のふつうのアプリケー ションは , 終了して DOS に制御を返すとき , INT21h ファンクション 4Ch(=End Proce ss ) のシステムコールを実行し , 自分が占めて いたメモリを DOS に返します。つまり DOS にとって , そのプログラムはメモリ上から 亡き者になります。 たとえばそのアプリケーションが , 実行 時にメモリ上て , 先頭の A 番地から終端の B 番地まてを専有していたとすると , それが 生きている ( =DOS の管理下にある ) とき は , 次に DOS が何かのためにメモリを割り 当てるときは , B 十 1 番地から先を使いま す。 しかし , ファンクション 4Ch の実行後は , DOS にとって使えるメモリが , かってその アプリケーションが占めていた A 番地以降に なってしまいます。 「亡き者になる」とは , おおざっぱにいう とこういうことてす。たとえば , そのアプ リケーションの終了後に別のアプリケーシ ョンをロード , 実行すると , それは A 番地以 降にロードされて , 走り始めるてしよう。 しかしアプリケーションが終了時に End Process のシステムコールてはなくて ,Keep 102 CMAGAZINE 1991 2 第の回 TS R の怪 岩谷宏 Process のシステムコール ( = INT21h , ファン クション 31h ) をコールすると , 上記の , 「 DOS にとって次に使えるメモリ領域は B 十 1 番地 以降だ」という状況が , そのアプリケーショ ンの終了後も残存します。すなわち A 番地か ら B 番地まてを占めているそのアプリケーシ ョンは , 終了後 DOS がどんなメモリ利用を しても , そこにそのまま , 無事に生き残り ます。だから , 起動する方法があれば , そ の A 番地以降に残っているプログラムを起動 て、きます。 A 番地から B 番地まて、を専有するあるアプ リケーションが KeepProcess を実行して終 了したあと , 別のアプリケーションをロー ド , 実行すると , それは B 十 1 番地以降にロ ードされて走り始めます。 WARNING: 上記では Keep されるプロセスの 使用最終番地である B 番地を , DOS が自動的 に検出して管理するかのように書いていま すが , それはウソです。 Keep Process シス テムコールには , Keep するメモリ量を , ユ ーザが引数として渡してやらなければなら ないのです。 TSR 作りを難しくしている状況 は数多くありますが , これもそのひとつで す。なぜなら , この引数の大きさが , 簡単 には決められないからです。 さて , MS-DOS が Keep Process というシ ステムコールを提供してくれていることは ありがたいとしても , しかし , その Keep さ れた Process を起動する , DOS サイドにおけ る標準的な方法は , 全然提供されていませ ん。もしも , そのための安定的な方法が提 供されるならば , MS-DOS はめて、たく , マ ルチタスク OS になりうるわけて、すが・・・ Keep された Process を起動するには , 割り 込みによるしかありません。実は 80 年代半 ばから , そういう TSR プログラムが , ポー ランド社の SideKick を初めとして , 市販ソ フトに登場してきたのて、す。 TSR がプログ ラミング雑誌の話題になってきたのは , そ ういう市販ソフトを見て , ホビイストプロ グラマたちも , 「どうやって作るんだろ , オ イラも作ってみたいナ」と考えるようになっ てきたからて、す。 今 , たとえば Turbo C や Turbo C 十十の ユーザにとって , いちばんおなじみの TSR プログラムは , あの HELP て、しよう。 ともかく , 市販の TSR ソフトは , あのよ うにキーポード割り込みを利用するものが いちばん多いようて、す。 ふつうの状態て、のキーポード割り込みル ーチンは , たとえば PC ー 9800 シリーズの場合 だと , 押されているキーを表す情報をバッ フアにどんどん積んて、いるだけ ( だそう ) て、 す。余談て、すけど , アスキーの「テクニカル データブック」 , 秀和の「解析マニュアル」 , 技術評論社の「 98 ハードに強くなる本」など , なぜどれも , PC ー 9800 シリーズのハードウェ ア割り込みに関するディテール情報がない のて、しようか。ソフトバンク様 , 今年あた り , 98 解析本の「決定版」を刊行してはいか がてしようか ? 余談の続きて、すが , 従来の解析本などに ードウェア割り込みに関する詳細情報が ノ、
List 4 0 sizeof を用いて , たとえば dou 団 e の配列を割 り付けたい場合には sizeof ( doub 囘などを渡 す。 2 番目は配列の階数 ( 次元の軸の数 ) てあ る。 3 番目以降は可変てあり , 2 番目の引数 て、指定した個数だけ各次元の要素数を順次 渡していく。 たとえば , 10X12X6 の 3 次元の doub の 配列を割り付けたい場合には , 次のように 使用する ( なおメモリ不足などて割り付けに 失敗すると , malloc( ) などと同様 NULL を 返してくるのて、実際にはそのチェックを行 うべきて、ある ) 。 double * * * p : fputs ( ” out Of memory ! }n ” stderr) : return 1 ; PRINT(a) ; PRINT(*a) ; PRINT(**a) ; PRINT(&a) ; PRINT(&aC0]) ; PRINT(&aC0]C0]) ; PRINT(&aC0][0]C0]); 16 17 19 20 22 23 24 25 Fig. 3 LSI C ー 86 Ve 「 .3.20 による prog2. c の実行結果 = 102 F Pointer value Of a Pointer value Of *a = 1033 Pointer value Of **a = 103 F =OE4C Pointer value Of &a Pointer value of &a[Ol = 102 F Pointer value of & a [ 0 Ⅱ 0 ] = 1033 Pointe 「 value of & a [ 0 Ⅱ 0 Ⅱ 0 ] = 103F このような構造をもたせると , 先に述べ た C の欠点のひとつ一一動的にサイズが変わ るような 2 次元以上の配列をパラメータて、渡 すことがて、きない を回避することがて きる。もちろんほかの手段て、も回避て、きる のだが , この手法は有力て、魅力的なものの p = (double* * *)aryalc(sizeof ひとって、ある。ただし , この手法て、は配列 (double), 3 , 10 , 12 , 6 ) ; 要素のアクセスごとに ( 次元数ー 1 ) 回のメモ (int* *)aryalc(sizeof(int), この関数を用いて 2 次元の int の配列を割り リアクセスが必要てあるということは覚え 付けて使用する例を List 3 , prog. c に示す 2 , 10 , 20 ) ; ておく必要がある。メモリアクセスが遅い という呼び出しが行われたとする。まず配 ( 当然ながら a 「 ya ℃ ( ) を呼んているのてリン マシンて、はこのコストが高いものにつく恐 列の本体を割り付ける。これは 10 x 20 x クする必要がある ) 。実際の使用にあたって れがある。 sizeof(int) バイトの連続領域があればよい は , 通常の配列のように使用てきるという もうひとつ注意すべきことは ,Fig. 3 の結 すなわち int [ 10 * 20 ] という 1 次元の配 ことがおわかりいただけるてあろう。 このようにして設定され 果が示すように 列を割り付ける。便宜上これを親配列と呼 どうしてこのようなことが可能なのか。 た多重ポインタはいくつかの点て、配列とは ばう。その配列のほかに , int * [ 10 ] すな その秘密は List 4 , prog2. c を (aryalc. c とリ 異なる性質を示すことて、ある。もっとも特 わち「 int へのポインタの 10 個の配列」を割り ンクして ) 動かしてみると推察てきるかもし 徴的なのは p と &p [ 0 ] [ 0 ] が異なるアドレ 付けるのてある。そのポインタ配列は , そ れない (Fig. 3 ) 。 ス値をもっことて、ある。 p は Fig. 3 から明ら れぞれが最初に確保された 1 次元配列の要素 本当の 3 次元配列を用いていた progl. c の かなようにポインタ配列の先頭要素へのポ 20 個おきのところをポイントするように初 実行結果とは異なり , 各ポインタ値が異な インタを意味している。一方 , &p [ 0 ] [ 0 ] 期化を行う。そしてこの配列の先頭要素へ る値を示していることにお気づきだろう。 これは * * p に等しい は親配列の先 のポインタを返すのてある。 先ほど , n 重ポインタを用いてアクセスする 頭要素へのポインタを意味している。 このような構造を作り上げることにより , 場合には , 途中て、メモリを参照しその値を 多次元配列をこのような構造て、実現する p [ 0 ] [ 0 ] は正しく親配列の先頭要素を , 使ラためにメモリに設定されているポイン と , 実はもうひとつの利点がある。たとえ p[l] [ 0 ] は親配列の 20 番目の要素を , pC2] タ値が何てあるかによって結果が変わると ば 3 角行列のように , 列ごとにサイズの異な 述べた。 a 「 ya ℃ ( ) はそのメモリへあたかも多 [ 0 ] は同じく 40 番目の要素を示すことカイき る配列を高いメモリ効率て、表現て、きるのて、一 次元配列をアクセスしているのと同じにな るのてある。以上は 2 次元配列をシミュレー ある。とくに最終的な各列が文字列 , すな るよう , つじつまを合わせられるようなポ わち文字の 1 次元配列て、あるような場合には トする場合だが , 3 次元以上の配列に関して インタ値を設定するのてある。 効果的て、ある。 main に渡される第 2 引数の も容易に拡張可能て , その場合にはポイン 説明を簡単にするために , 比較的わかり char * * a 「 gv がこの技法を使って表現され タ配列が ( 次元数ー 1 ) 個だけ ( 理論的には ) 個 やすい 2 次元配列を例に取って説明しよう。 ているが , それはまさにこの理由から多次 別に用意されて何重にもポインタが張り巡 元配列をポインタ配列を用いて表現してい らされることになる (Fig. 4 ) 。 int * * p , P 116 CMAGAZINE 19 2
EXE 386 メモリ環境は弸から開放された / EXE286 好評発売中 ) DOS 工クステンタ ・ VC 対応・ DP Ⅶ対応予定 : XE386 は、 80386CPU のプロテクトモードでユーザプロクラムを実行 、せるための DOS 工クステンダで魂 MS - DOS の環境をそのまま利用 て 4G Bytes の広大なメモリ空間をリニアにアクセスするプログラムが き行できま魂処理系は、 High C386 , NDP FORTRAN386, MA , TASM の言語が利用できます。また GNIJ C も動作可能ですさ に大規模プログラム開発に不可決な高機能ソースレベルデバッガ PARTNER - V3.1 相当の機能 ) が付属ぽいます。また専用のリンカ 付属します *.NDP FORTRAN 3 のコンハイルには P ト ar L 叩社の TOOL BOX が必要てす ) 動作環境 種 : 80386 / 80486 の CPIJ を搭載した PC - 9800 または互換機 ' モリ : 増設メモリ ( プロテクトモード用 ) IM パイト以上 ) S : MS-DOS Ve 「 3.1 , 3.3 ) 価格 DOS 工クステンダ十テンヾッガ ) 100 本分の DOS 工クステンダのライセンス十テンヾッガ ) 1 , 000 本分の DOS 工クステンダのライセンス十テンヾッガ ) 0 43 , 000 円 198 , 000 円 990 , 000 円 Ⅸ E386 開発キット Ⅸ E386 ライセンスパック 100 Ⅸ E386 ライセンスパック 1000 80386 用 DOS ェクステンダ ( EXE386 ) 無償版配布中 / EXE286 386 は、非営利目的には無償でご使用いただけます。手数料 2.000 円 ( 定額小為替 ) を同封して当社 DOS ェクステンダ係まてお申し込み下さい。 ( 但し有料のパッケーシとは、若干の違いがあります。 ) をライセンスパックは、 EXE386 を組込んだアプリケーションを、販売または 利目的で利用するためのライセンスです付属のシールを製品に 占り付けて下さい。これ以外の契約形態についてはお問い合せ下さい。 京都マイクロコンピ、 ータ株式会社 〒 617 京都府長岡京市長岡 3 丁目 1 ー 2 TEL ( 075 ) 953-0963 FAX ( 075 ) 953 ー 0935 く資料請求番り・ 003
五ロ はじめて学ふプロクラー ニンク 藤澤昌聡さんの解答 ( ta ⅱ . c ) このプログラムの欠点はリスト構造にし ながら , 入力される文字をすべてメモリに 寺しているので , メモリのムダ遣いをし ている点カげられます。 まあ , のコンピュータは昔と違って こならメモリにがあるのでよい のでしようが・・・・・・。改良しようと思えば いらなくなった行を含むリストをフリーし てしまうことカ考えられますね ( とこ ろ , パソコン系ではメモリをフリー しても , そ賦を再割り当てできる 系は悲しいことに私カ加っているかぎり なしで , そのようにしてもムダなん 藤澤さんのプログラムにはいかにも 語らしいトリッキーな部分があるので , 説 明しておきましよう。 17 ~ 2 テ目の NODE 型宣言では cha 「型きさ 1 己 列 body カ喧言されていますれこれを見 て「なんだこれは ? 」とめれた方もいる と思います。 4 ラ目で , この NODE 型のポ インタ tmp に NODE 型の大きさ 十 バッファⅱ ne に 1 彳冗み込まれた文字 分の大きさ の領域を確保してその先頭ポインタを NODE * 型にキャストしてイ及していま す。構のメン / ヾは宣言された順番に メモリにされます。こーによ ってメンバ駄きさ 1 の ch 田型己列 body 窈麦ろにノヾッファⅱ n 売み込まれた文字 分賦カして確保されているのです。 従って , メン / ヾ body は自分自身の大きさも 合わせて , あたかも バッファⅱ n 売み込まれた文字 きさ List 20 2 : ta i l. c : C 言語入門講座 9 0 年 11 月号クイズ 3 : OS : MS-DOS 3.30 4 : Compiler : Turbo C 2. 0c 5 : date : 1990. 10.28 auther : K I NT A 7 : 8 : 9 : #include く stdio. h> 10 : #include く string. h> 11 : # i nc I ud e く a Ⅱ oc. h > / * Turbo C では a110C * / 12 : 13 : #define MAX BUPSIZ + 2 / * 配列用最大値 * / 14 : #define DEF_N TAI し 10 / * 表示行数のテ・フォルト値 * / 16 : / * 読み込み用構造体 ( 参 : 同号 C 言語雑学講座 ) * / 17 : typedef struct node { struct node *next; body[l]; Char 20 : } NODE; 22 : 23 : / * argc を使っていないのでコンパイル時に警告がでます (* 24 : VOid main( int argc char **argv ) 26 : NODE *head = NULL, / * 表示用先頭ポインタ * / *tai 1 ニ NU しし , / * 挿入用末尾ポインタ * / 28 : / * 挿入用一時ポインタ * / = NU しし: *tmp 29 : line [MAX] : Char 1 行読み込み用パッファ 30 : FI し E *fp = NU しし: / * ファイルポインタ * / 31 : int lcnt / * 読み込み中行番号 * / 32 : int / * 表示用行数 * / n_tail = DEF_N_TAIL; 33 : / * 引数のチェック & ファイル O P E N * / 34 : i f (strchr (* 十十 argv, 35 : / * 表示行数指定が無意味・無謀な場合はテ・フォルト値 * / 36 : 37 : if ( (n_tail = atoi ( + + (*argv + + ))) く = 0 ) n_tai 1 = DEF_N_TAIL,• 38 : if ( (fp fopen (*argv, "rt")) 39 : ニ NU しし ) { 40 : / * 指定ファイル名が無効または無指定の場合は標準入力 * / std i n : 42 : 43 : 44 : 45 : 46 : 48 : 49 : 50 : 52 : 53 : 54 : 55 : 56 : 59 : 60 : 69 : / * テキストのヒープ領域への読み込み * / whi le (fgets(line, MAX, (p) !=NU しし ) { if ( (tmp = (NODE *)maIIoc(sizeof(NODE) + strlen(line)) )==NULL ) { printf("Not Memory!!") : exit( の : strcpy (tmp->body, 1 i (e) : 十十 nt : tmp->next=NUL し : if (head==NUL し ) { head = tmp : } else { ta i l->next=tmp; / * 1 回目の読み込み * / / * 2 回目以降の読み込み * / tail=tmp; if (lcnt>n_tai l) head=head->next;/* 表示行数分 head を移動 * / c lose (fp) : tmp=head; while (tmp!=NU しし ) { printf("Xs", tmp->body) : tmp=tmp->next; / * head から全行を表示 * / 十 1 己列として扱うことができるのです。 はじめて学ぶ C プログラミング 129
に一売 List 変換します。 アドレス解決の方法 List 7 を参照してください 残念ながらプログラムとデータの同位置 番地への割り当ては , このソースて、はエラー としてはねています ( 68000 のハード側て、は データ参照とプログラム参照は厳密に区別 されていますが , X68000 て、は同一メモリ空 間てす ) 。 付録に収録されたプログラムては , data セクションと common セクションを分離して いないのて、うまくいきません ( 本当に手抜き 時間がなかったものて、ワーニン て、す・・ グは出しますが処理は何もしてません ) 。 Human68k< はコンノヾータのソースを変更 して , 初期値つき data 部はポインタの値を ターゲット ROM, RAM のアドレスに適合 するように変更しながら別ファイルに書き 出しておけばよいと思います。 余談になりますが , 68 系の ROM 化システ ムとして有名な OS9 て、は , このあたりは OS レベルて、解決しています。 OS9 て、はプロセス ( プログラム ? ) に与えられるデータのサイ ズ , 初期化データサイズ , スタックの要求 量がモジュールヘッダと呼ばれる部分に記 述されています。 OS はこれらを参照して現 在フリーなメモリを獲得して , 初期化され るべきデータをそこにコピーし , スタック を設定し , 割り当てたデータ領域 ( RAM 領域 ) の先頭を a6 に設定してプログラムを実行し ます。プログラムは大域変数を , a6 をベー スアドレスとした相対値てアクセスします。 この前提を守っているかぎり , OS9 のプログ ラムは完全にリロケータブルてリエントラ を生成することて解決しています。 C 言語て コーディングするときには当然 ROM 化を ントてす。 OS9 て、稼働する C コンパイラはす ROM 化を考える場合には , 相当スマートて 考慮しておく必要があります。文字列リテ べてこの前提を満たすコードを出力します。 美しい方法てしよう。詳しく知りたい場合 ラルは変更てきません (-fwritable-strings を bsr 命令て、届かない ( 士 32K バイトを越える は , OS9 のマイクロウェア C のマニュアルを GCC ては指定しておけば文字列は data セク サプルーチンコール ) は , あらかじめリンカ 参照してください ( もっとも , 68000 ては 6809 ションに出力されますが・・・・・・。変更する行 がこれをモジュール内部に記録しておき , の OS9 ほど美しくないと思うのてすが・・・ 為自体に問題がありそうてす ) 。文字列ポイ プログラム起動時に OS がジャンプテープル bsr の制限などがしつくりしないのて、 ) 。 ンタを返す関数て , ポインタの値として文 実行アドレスを $ 120000 に指定して、データ領域の先頭を $ 4000 に指定 してコンバートしたバイナリ 00120000 $ 00004100 , A7 lea $ 0012000E 00120006 JSr $ 0012000C 0012000C bra. S D3, -(A7) 0012000E move. 1 # $ 00 , D3 00120010 moveq D3, DO 00120012 move. ー # 8 , D0 00120014 as l. 1 # $ 00004100 , DO 00120016 add.l DO, -(A7) 0012001C move. ー $ 00120032 0012001E JSr 00120024 # 4 , A7 addq. w # 1 , D3 00120026 addq. I 00120028 # $ 02 , DI moveq 0012002A D3, DI cmp. 1 0012002C $ 00120012 bge. s ( A7 ) + , D3 0012002E move. ー 00120030 rts movea.l $ 0004 ( A7 ) , A2 00120032 00120036 movea. w #$COOI, AI 0012003A movea. w # $ C003 , A0 0012003E # $ 00 , DI moveq (AO),DO 00120040 move. b 00120042 $ 00120040 beq. s ( AI ) , $ 00 ( A2 , DI. l) 00120044 move. b # 1 , DI 00120048 addq.l 0012004A # $ 000000FF , DI cmp. 1 00120050 $ 00120040 い e. s 00120052 rts 0 $ 00000000 ↓メモリ上位 base text end=data base bata end プログラム (text section) 初期値つき data (data section) ← . X ファイルのヘッダに 位置が書いてある ← . X ファイルのヘッダに 位置が書いてある ↓メモリ下位 $ f 絎 初期値なし (common section) 142 CMAGAZINE 1991 2
CPAD COMPUTER PRO-STAFF SYSTEM CREATE 登録彑ー し mo 「登 0 Fig. 4 疑似 2 次元配列のポインタ構造 ポインタ配列 int [ 10 ] 0 1 2 3 多重ポインタ int int [10*201 0 1 、に IJ 高品質のュメ万一ションを簡単に実現する、 新世代のプロジェクト指向プログラムヘルバーてす。 CPAD はこれまて C 言語による開発てソフトハウ スが悩んて、いた、開発時の工数短縮及び複数 人数によるプロジェクト管理を容易に致します。 また、既存のソースリストの仕様書を自動作成し ますの ( 管理体制を容易に画一化することが 可能となり、また、プログラマーの余分な負担を 軽減する事がて、きます。 20 7 8 9 29 30 0 179 180 199 ト 2 ・¥ 85 , 000 98 シリーズ対応版 5 大機能 c ソースの解析、援助、学習ツールとして ① C 言語ソのドキュメント管理を自動化、一律化する。 ②カーコ \ ン & リッチーの書式にソースをリフォーム。 ③ PAD 仕様に準ずる出力機能。 ( 自動出力印刷例参照 ) ④全ドキュメントはエテイタて編集可能。 ⑤豊富な出力機能。 ( 自動出力印刷例参照 ) ソフトウェアインフォメーションセンター く技術的なこ質問・こ相談に電話でお答えします ) TEL. ( 06 ) 634 ー 2563 〒 556 大阪市浪速区日本橋東 3 丁目 2 ー 23 受付時間 / 想 9 : ~ 5 : 月曜日 ~ 金曜日 ( 祝日を除く ) : オオッカ商事 / ー、、本社 : 〒 760 高松市西内町 5-14 く資料請求番号 1 17 〉 ANSI C : more 117 るのだといえる。 こて、示したポインタを利用した間接ア [ 注 1 ] 仮想記憶のマシンでは , メモリは ドレスによる多次元配列の基本アイデアは 512 バイトから 16K バイト程度 ( マシンによ C 言語の先祖のひとってある BCPL て、使われ って違う ) の大きさのページという単位で管 ている。 BCPL て、は配列のことをベクタと呼 理されている。アクセスしようとしたある ぶが , 言語仕様としては 1 次元のべクタしか 仮想アドレスのメモリが実メモリ上に存在 用意されていなかった。そのためこのよう しないことをベージフォルトと呼ぶ。ペー なポインタの配列を利用することて一見多 ジフォルトが起きると OS に制御が移り , 2 次 次元の配列て、あるかのように見せかける手 記憶装置 ( 通常 H D) と主記憶との間でページ の入れ換え , すなわちページングが起きる。 法を用いていたのてある。 C てはいちおう配 ページングが行われている間はプログラム 列の配列という形式て 2 次元配列を導入した の実行が中断するため , ページフォルトの が , 残念ながらいくっかの点て使いにくい 頻度が高くなるとそれだけ実行速度が低下 占が残ってるが , ここて示した技法を知っ する。 ておくことは決してムダにはならないだろ
データは扱っていません。というより , コ す。これは [ X 形式 ] なのて、 , Human68k が なしデータ領域 ( BSS セクション ) とプログラ ンバータが手抜きなのて、 data セクションを 空いているメモリ領域に適当にリロケート ム領域 ( TEXT セクション ) のそれぞれのアド 分離していないのて、す。 X ファイルは Fig. 1 して List 5 のようにメモリに展開されます。 レスを指定して絶対番地実行可能な純粋バ のようにメモリに展開されます。 イナリを出力するプログラムを作成しまし List 6 がコンバートされた純粋なバイナリ Fig. 1 に記入してあるリロケート情報はす をメモリに読み込んて、 , デバッガて、逆アセ た。短期間て、作成したのて、まだバグがある べて [ X 形式 ] ファイルに記録されていま ンプルしたものてす。 かもしれませんが , ソースを付録ディスク す。コンバータブログラムて、はファイルに に収録しましたのて、参考にしていただけれ , 初化テータが存在する場合 含まれるリロケート情報を参照して , 各オ ば幸いて、す。 ペランドの示すアドレスがどの領域を示す 話を戻します。コンパイルされた結果を のかを計算して , 変換後の参照アドレスに デバッガて、逆アセンプルしたものが List 5 て、 この簡単なサンプルて、は , 初期化された List LiSt 1 : v 0 i d 2 : getbuffer(char *buf) 4 : =(char * ) 0xffffc001; register char *portl register volatile char *port2 =(char * ) 0xffffc003; 6 : register int i = 0 : wh i 1 e ( i く 256 ) { 7 : 8 : while (*port2 buf [ i + + ] 9 : *portl; 1 : vo i d 2 : getbuffer(char *buf) =(char * ) 0xffffc001 : 4 : register char *portl register volatile char *port2 =(char * ) 0xffffc003; 5 : 6 : register int i = 0 : wh ⅱ e ( i く 25 6 ) { 7 : whi le (*port2 buf [ i + + ] 9 : *portl : Li st LiSt 1 : * NO_APP 2 : peaW macro 3 : $ 4878 , . dc. w 4 : endm 5 : * ÅPP ON (APP) 6 : . text 7 : lea -stacktop + 256, a7 8 : jsr -start 9 : bra * 11 : * APP OFF (NO_APP) 12 : . text . even . g10b1 -start start : move. 1 d3, -(sp) 17 : moveq. 1 # 0 , d3 move. 1 d3,d0 20 : asl. 1 # 8 , d0 add. 1 #_buffer, d0 move.l d0, -(sp) 23 : jsr -getbuffer 24 : addq. w # 4 , sp 25 : addq. 1 # 1 , d3 26 : moveq. 1 # 2 , dl cmp.l d3, dl bge ? 5 29 : move.l (sp) + , d3 30 : rts . bss 32 : xdef 33 : comm 34 : xdef 35 : comm 36 : . end シンポル情報が付加されているので、その情報が表示されています。 00119CD0 $ 00119E24. _buffer, A7 lea $ 00119CDE. _start 00119CD6 JSr bra. s $ 00119CDC 00119CDC start: move.l D3, -(A7) 00119CDE 00119CE0 moveq # $ 00 , D3 move.l D3, D0 00119CE2 # 8 , D0 00119CE4 as 1 コ 00119CE6 add. 1 # $ 00119E24. _buffer, DO move.l DO. -(A7) 00119CEC $ 00119D02. _getbuffer 00119CEE JSr addq. w # 4 , A7 00119CF4 addq.l # 1 , D3 00119CF6 # $ 02 , DI 00119CF8 moveq D3,Dl 00119CFA cmp. ー bge. s $ 00119CE2 00119CFC ( A7 ) + , D3 00119CFE move. ー 00119D00 rts -getbuffer: 00119D02 00119D06 00119DOA 00119DOE 00119D10 00119D12 00119D14 00119 D 18 00119 D 1 A 00119D20 00119D22 stacktop : 00119D24 00119D28 val val movea. 1 $ 0004 ( A7 ) , A2 movea. w # $ C001 , AI movea. w # $ C003 , AO moveq # $ 00 , DI move. b (AO) , DO beq. s $ 00119D10 move. b ( AI ) , $ 00 ( A2 , DI. l) addq.l # 1 , DI # $ 000000FF , DI cmp. ー $ 00119D10 ble. s rts stacktop stacktop, 256 buffer -buffer, 768 ori. b # $ 00 , D0 ori . b # $ 00 , DO Conference Room 141
い。その埋め合わせに , ccxx て、は Glocken ーて、ある。 spiel のて、はなく , 使用する C コンパイラのプ インストールは 6 段階の処理て、行う。ほか lmageS0ft . の C 十十に比べると手作業が多いのて、ある リプロセッサを使うことがて、きる。 TabIe 2 Glockenspiel C ナ当き讐 が , それらは入念て、 , さほど苦にはならな に示すように ccxx の Plum-Hall sampler の 成績は , MicrosoftC のプリプロセッサを使 トランスレータにはリアルモード用 , プ ったときのほうが優秀て、ある。 Glockenspiel C 十十 Ver. 2. Oa は AT & ロテクトモード用 , そして拡張メモリ用の Glockenspiel は Microsoft の Programm T 2.0 をベースとし , Microsoft C Ver. 6.0 各バーションがある。相性の悪い常駐プロ er's Workbench(PWB) を C 十十の統合環境 または Ver. 5.1 をバックエンドとして使用 グラムがあると , プロテクトモード用は使 として構成するためのファイルを提供して する。メモリモデルは large モデルだけをサ えない場合があるとマニュアルは警告して いる。しかしそれを使えるようにするため ポートしている。 には , 1 時間ぐらいかけて , ファイルの内容 パッケージ全体はケース入りのバインダ いる。早速試してみると , トランスレータ は "free store exhausted ( メモリ不足 ) 〃と を苦労して変えなければならなかった。 になっている。ューザーズガイドの部分 , いうエラーメッセージを出して停止した。 ったん使えるようになると , PWB はたしか コンノヾイラとシンタクスのマニュアル , ラ にコマンドラインより便利て、あるが , しか 常駐のコマンドラインエデイタて、ある ced を イプラリのガイド , およびインデクスとい し Turbo や Zortech の環境に比べると子ども アンロードしたら , この問題は消えた。 った各部分は , タグっきの中表紙て、わかる この処理系は支援ツールをふたっしか提 だまして、ある。私は PWB 互換の QuickHelp ようになっている。シンタクスガイドは AT& 供していない。コンパイラドライバと名前 機能を試してみる時間がなかった。ライプ T の 1989 年 5 月の C 十十 Reference Manual 復旧ユーティリティて、ある。ドライバには をもとにしている。 14 ページの、、 Read Me ラリは iostream と stream と複素数クラスを 複数のソースファイル , オプジェクトファ First" という小冊子にリリースノートがある。 提供しており , ライプラリガイドに詳しい イル , そしてライプラリファイルを渡して , その小冊子には , ドキュメンテーションに 説明がある。 実行ファイルを構築て、きるのて便利て、ある。 Dewhurst&Stark の Programming in C Glockenspiel C 十十は , そんなにロバス 十十〃 ( 日本語版℃ + 十言語入門』アスキ プリプロセスだけ , プリプロセスして cfront ト (robust, 堅牢 , 堅固 ) て、はない。最適化オ ー出版局 ) が含まれていると書かれている を実行するだけ , オプジェクトファイルへ プションを Microsoft C に渡そうとしたとき が , 私が受け取ったパッケージには入って コンパイルするだけ , といったオプション ときどきアポートした。 tawk のコ などに いなかった。ソフトウェアは 3 枚の 1.2M バ もある。ドライバは C コンパイラへのオプシ ンパイルとリンクはて、きたが , プログラム イトフロッヒ。ーに入っている。そのうちの ョンも渡せる。しかし . c ファイルも C 十十の は正しく実行て、きなかった。 ひとつは OS / 2 用のバージョンて、あるが , そ ソースとみなすのて、 , コマンド行に C 十十と lntek egration Technologies れは今回テストしなかった。 C のソースを混在させることがて、きない。ラ 小冊子、、 Read Me First" に簡単なイン イプラリには iostream. h とともに ,Ver. 1. x C 十十 Ver ム 0a ストールガイドが書かれている。インスト のプログラムとの互換のために stream. h も ール用のユーティリティは , 使い方はやさ 入っている。ライプラリのクラスに関して lntek C 十十 Ver. 2 . 0a も AT&T 2 . 0 の と しいのだが , 結果が気にいらなかった は説明文書が何もない ライセンシーて、あるが , 使える C コンパイラ くに気にいらなかったのが , C の標準ヘッダ cfront 2.1 の処理系をテストて、きると思っ の種類は Comeau や Glockenspiel より多くな の C 十十版を作ってくれない点て、ある。私は てワクワクしたのて、あるが , 異常停止の回 っている。私はこれを , Turbo C Ver. 2.0 1 ~ 2 時間かけて , C のヘッダを正しくインス 数があまりにも多いのて、幻滅した。 C 十十の と WatcomCVer. 7.0 て、テストした。これ トールするためのツールを作らなければな 基本機能のテストて、も成績が悪く , テスト は large 以外のメモリモデルをサポートして した中規模 ~ 大規模なプログラムのほとん らなかった。 いる唯一の cfront システムて、ある。 コンノヾイラドライノヾの ccxx は , Comeau ・どがコンパイルてきなかった。しかし , よ ソフトウェアは 2 枚の 1.2M バイトフロッ のより便利にて、きている。 1 回のコンパイル い点もある。コンパイラ殺しの陰性のテス ヒ。ーに入っている。ドキュメンテーション コマンドに C と C 十十のソースファイルを併 ト ( コンパイルて、きないことが合格となるテ は 8.5 x 11 インチという用紙サイズて、 , 3 穴 パンチだが , バインダにはなっていない 己することがてきる 0Glockenspiel は独自の この製品 スト ) ては , 最高得点て、あった。 プログラマズガイドが 40 ページ , リリース プリプロセッサを提供しているが , それは は , もう少し安定してから , もう一度テス ノートが 3 ページ , そして残りが , AT&T 2.0 これを ANSI C の機能のすべてはサポートしていな トしてみたいと思う。それまて、は , 52 CMAGAZINE 1991 2 推奨て、きない 1 三ロ
TabIe 1 各コンノヾイラの機能特性 Comenu C 十十 2 . 1 G10kenspieI C 十十 2. Oa Turbo C 十十 1 .0 Zortech C 十十 2 .0 lntek C 十十 2 . Oa ユーティリティ 統合環境 リンカ ライプラリアン make オンラインヘルプ アセンプラ テノヾッガ プロファイラ 名前復旧機能 C 十十フロントエンド バックエンドコンノヾイラ P refe 「「 e d Others 0 0 0 0 0 0 0 0 0 0 0 0 Q) 0 0 0 Yes Yes Yes Yes Yes No Yes3 No No Yes Yes Ye s Yes Yes Yes Yes2 Yes2 Yes4 N /A 1 0 0 0 0 0 0 0 0 2 AT&T cfront 2 .0 AT&T cfront 2 .0 AT&T cfront 2 . 1 N /A N /A N /A Microsoft 6.0 Metaware 386 1 . 5 Lattice 6 .0 Microsoft 5.1 Microsoft 5.1 Turbo 2 .0 Watcom 386 7 .0 Watcom 7 .0 Microsoft 6.0 Microsoft 5. 1 メモリモテル Tiny Small Medium Compact Large Huge Keywords(near, 八一ドウェア最小要件 プロセッサ / メモリ 八一ドティスク容量 C 十十ライプラリ stream iostream 複素数 コンテナクラス 汎用テータ No 構造体 No DOS インタフェイス 1 . Mic 「 osoft の PW 日 ( プログラマーズ・ワ - クベンチ ) を C 十十の環境として構成するための ファイルを提供している 2. プロフェッショナル版のみ 3. DeveIooe 「・ s Edition のみ 48 CMAGAZINE 1991 2 Yes Yes Yes Yes Yes Ye s Yes 0 0 0 0 0 Q) Yes Yes Yes Yes Yes Yes Yes Ye S5 Ye S5 Ye S5 Yes5 Yes5 Yes5 Yes 0 0 0 0 0 0 80286 / 1 .5M 八イト 8086 / 640K バイト 80286 / 1 .5M バイト 80286 / 1 .5M バイト 80386 / IM ノヾイト 1 .5M ノヾイト 3M バイト 1 .5M バイト IM ノヾイト 8086 / 512K ノヾイト 3M バイト Yes No Ye s No Yes Yes Yes Yes Ye s Ye s Ye s No Yes Yes Yes Ye S6 Yes Yes No No No No No No Yes Ye s No No 3 4. 加工前の名前かメッセーシ中に自動的に表示される 5. 八ックエンドの C コンパイラによる。丁凵「 00 C は全部サポートしている 6. Commonview SDK(C 十十 1 2 用 ) のみ