(57)【要約】【課題】ターゲットプログラムから互いに依存関係のある文の集合を正しく抽出する。【解決手段】本発明の一態様としてのプログラム解析装置は、複数の文を含むターゲットプログラムと、複数の変数にアドレスを割り当てたアドレス定義データとの入力を受け付ける手段と、前記文毎に前記定義変数と前記参照変数のアドレスとを対応付けたアドレス間定義−参照データを生成する手段と、前記定義変数のアドレスと、前記定義変数を含む文の行番号と、前記定義変数と同一アドレスの参照変数を含む文の行番号とを対応付けたアドレス依存データを生成する手段と、前記ターゲットプログラムから制御文と前記制御文の実行結果に依存して実行される制御対象文とを検出し、これらの行番号を対応付けた制御依存データを生成する手段と、指定された行番号の文を始点とし、前記制御依存データおよび前記アドレス依存データに基づいて到達する文の集合を抽出するスライス抽出手段と、を備える。【選択図】図１
2009237762.tif 000002
【特許請求の範囲】
【請求項１】
複数の文を含むターゲットプログラムと、前記ターゲットプログラムで用いられる複数の変数にそれぞれアドレスを割り当てたアドレス定義データと、の入力を受け付ける入力受付手段と、
前記入力受付手段に入力されたターゲットプログラムに含まれる各文の各々から定義変数と参照変数とを検出し、前記文毎に前記文の行番号と前記定義変数のアドレスと前記参照変数のアドレスとを対応付けたアドレス間定義−参照データを生成するアドレス間定義−参照データ生成手段と、
前記アドレス間定義−参照データに基づき、前記定義変数のアドレスと、前記定義変数を含む文の行番号と、前記定義変数と同一アドレスの参照変数を含む文の行番号とを対応付けたアドレス依存データを生成するアドレス依存データ生成手段と、
前記ターゲットプログラムから制御文と、前記制御文の実行結果に依存して実行される制御対象文とを検出し、前記制御文の行番号と、前記制御対象文の行番号とを対応付けた制御依存データを生成する制御依存データ生成手段と、
前記ターゲットプログラムにおける所望の行番号をスライス基準として指定するスライス基準指定手段と、
前記スライス基準として指定された行番号の文を始点とし、前記制御依存データおよび前記アドレス依存データに基づいて到達する文の集合を前記ターゲットプログラムからスライスとして抽出するスライス抽出手段と、
を備えたプログラム解析装置。
【請求項２】
前記ターゲットプログラムにおける前記複数の変数は共用体の変数を含み、前記アドレス定義データは前記共用体の変数にアドレスを割り当て、
前記アドレス間定義−参照データ生成手段は、前記共用体のメンバ変数のアドレスとして、前記共用体の変数のアドレスを用いる
ことを特徴とする請求項１に記載のプログラム解析装置。
【請求項３】
前記ターゲットプログラムからアドレスを用いた演算を行っている文を検出し、検出した文において、アドレスが呼び出されている呼び出し元変数と、前記アドレスの演算値が代入される代入先変数とを特定し、前記代入先変数のアドレスと前記呼び出し元変数のアドレスとを対応付けたアドレス間参照関係データを作成するポインタ解析手段をさらに備え、
前記アドレス間定義−参照データ生成手段は、前記代入先変数と同一のアドレスをもつ参照変数のアドレスを前記呼び出し元変数のアドレスへ置換し、
前記スライス抽出手段は、前記制御依存データおよび前記アドレス依存データに加えて、前記アドレス間参照関係データにさらに基づいて、前記スライスの抽出を行う
ことを特徴とする請求項１または２に記載のプログラム解析装置。
【請求項４】
前記ターゲットプログラムから配列を宣言した文を検出し、検出した文を解析することにより前記配列のサイズを取得する配列サイズ解析手段をさらに備え、
前記アドレス間定義−参照データ生成手段は、インデックスが変数により指定された配列である定義変数または参照変数については、前記配列のサイズに応じたすべてのインデックス候補に対応するアドレスを前記定義変数または前記参照変数のアドレスとして用いる
ことを特徴とする請求項１ないし３のいずれか一項に記載のプログラム解析装置。
【請求項５】
前記アドレス定義データは前記ターゲットプログラム中に記述されたことを特徴とする請求項１ないし４のいずれか一項に記載のプログラム解析方法。
【請求項６】
複数の文を含むターゲットプログラムと、前記ターゲットプログラムで用いられる複数の変数にそれぞれアドレスを割り当てたアドレス定義データと、の入力を受け付ける入力受付ステップと、
前記入力受付ステップで入力されたターゲットプログラムに含まれる各文の各々から定義変数と参照変数とを検出し、前記文毎に前記文の行番号と前記定義変数のアドレスと前記参照変数のアドレスとを対応付けたアドレス間定義−参照データを生成するアドレス間定義−参照データ生成ステップと、
前記アドレス間定義−参照データに基づき、前記定義変数のアドレスと、前記定義変数を含む文の行番号と、前記定義変数と同一アドレスの参照変数を含む文の行番号とを対応付けたアドレス依存データを生成するアドレス依存データ生成ステップと、
前記ターゲットプログラムから制御文と、前記制御文の実行結果に依存して実行される制御対象文とを検出し、前記制御文の行番号と、前記制御対象文の行番号とを対応付けた制御依存データを生成する制御依存データ生成ステップと、
前記ターゲットプログラムにおける所望の行番号をスライス基準として指定するスライス基準指定ステップと、
前記スライス基準として指定された行番号の文を始点とし、前記制御依存データおよび前記アドレス依存データに基づいて到達する文の集合を前記ターゲットプログラムからスライスとして抽出するスライス抽出ステップと、
を備えたプログラム解析方法。
【請求項７】
前記ターゲットプログラムにおける前記複数の変数は共用体の変数を含み、前記アドレス定義データは前記共用体の変数にアドレスを割り当て、
前記アドレス間定義−参照データ生成ステップは、前記共用体のメンバ変数のアドレスとして、前記共用体の変数のアドレスを用いる
ことを特徴とする請求項６に記載のプログラム解析方法。
【請求項８】
前記ターゲットプログラムからアドレスを用いた演算を行っている文を検出し、検出した文において、アドレスが呼び出されている呼び出し元変数と、前記アドレスの演算値が代入される代入先変数とを特定し、前記代入先変数のアドレスと前記呼び出し元変数のアドレスとを対応付けたアドレス間参照関係データを作成するポインタ解析ステップをさらに備え、
前記アドレス間定義−参照データ生成ステップは、前記代入先変数と同一のアドレスをもつ参照変数のアドレスを前記呼び出し元変数のアドレスへ置換し、
前記スライス抽出手ステップは、前記制御依存データおよび前記アドレス依存データに加えて、前記アドレス間参照関係データにさらに基づいて、前記スライスの抽出を行う
ことを特徴とする請求項６または７に記載のプログラム解析方法。
【請求項９】
前記ターゲットプログラムから配列を宣言した文を検出し、検出した文を解析することにより前記配列のサイズを取得する配列サイズ解析ステップをさらに備え、
前記アドレス間定義−参照データ生成ステップは、インデックスが変数により指定された配列である定義変数または参照変数については、前記配列のサイズに応じたすべてのインデックス候補に対応するアドレスを前記定義変数または前記参照変数のアドレスとして用いる
ことを特徴とする請求項６ないし８のいずれか一項に記載のプログラム解析方法。
【請求項１０】
前記アドレス定義データは前記ターゲットプログラム中に記述されたことを特徴とする請求項６ないし９のいずれか一項に記載のプログラム解析方法。
【請求項１１】
請求項６ないし１０のいずれか一項に記載の各ステップをコンピュータに実行させるための命令コード群を備えた解析プログラム。
【発明の詳細な説明】
【技術分野】
【０００１】
本発明は、プログラム解析装置、プログラム解析方法および解析プログラムに関し、たとえばプログラムに含まれる変数間の依存関係を解析する技術に関する。
【背景技術】
【０００２】
ターゲットプログラムにおいて注目している文に対し、影響を与えるまたは影響を受ける可能性のある文の集合をスライス（プログラム断片あるいは部分プログラム）として抽出する手法としてプログラムスライシングが従来からある。
【０００３】
従来のプログラムスライシングでは、変数名に注目して、依存関係のある文を特定し、抽出する。このため、ある変数と、別の変数とがあり、これらの変数が同一のアドレスを指す場合、これらの変数を依存関係がないとして扱ってしまう問題がある。また共用体の変数などが含まれたプログラムでは、別々の変数（メンバ変数）が同一のアドレスに定義されており、変数のひとつが変化すると残りの変数が全て変化する。各変数はそれぞれ別個のものとして扱われてしまうため、共用体の変数などが含まれたプログラムでは、スライスを正しく抽出できなかった。その他、配列またはポインタなどを含むプログラムに対しても同様に正しくスライスを抽出できなかった。
【非特許文献１】WEISER、Program Slicing
【非特許文献２】Ottenstein、The program dependence graph in a software development environment.
【発明の開示】
【発明が解決しようとする課題】
【０００４】
本発明は、ターゲットプログラムから互いに依存関係のある文の集合を正しく抽出することを可能としたプログラム解析装置、プログラム解析方法および解析プログラムを提供する。
【課題を解決するための手段】
【０００５】
本発明の一態様としてのプログラム解析装置は、
複数の文を含むターゲットプログラムと、前記ターゲットプログラムで用いられる複数の変数にそれぞれアドレスを割り当てたアドレス定義データと、の入力を受け付ける入力受付手段と、
前記入力受付手段に入力されたターゲットプログラムに含まれる各文の各々から定義変数と参照変数とを検出し、前記文毎に前記文の行番号と前記定義変数のアドレスと前記参照変数のアドレスとを対応付けたアドレス間定義−参照データを生成するアドレス間定義−参照データ生成手段と、
前記アドレス間定義−参照データに基づき、前記定義変数のアドレスと、前記定義変数を含む文の行番号と、前記定義変数と同一アドレスの参照変数を含む文の行番号とを対応付けたアドレス依存データを生成するアドレス依存データ生成手段と、
前記ターゲットプログラムから制御文と、前記制御文の実行結果に依存して実行される制御対象文とを検出し、前記制御文の行番号と、前記制御対象文の行番号とを対応付けた制御依存データを生成する制御依存データ生成手段と、
前記ターゲットプログラムにおける所望の行番号をスライス基準として指定するスライス基準指定手段と、
前記スライス基準として指定された行番号の文を始点とし、前記制御依存データおよび前記アドレス依存データに基づいて到達する文の集合を前記ターゲットプログラムからスライスとして抽出するスライス抽出手段と、
を備える。
【０００６】
本発明の一態様としてのプログラム解析方法は、
複数の文を含むターゲットプログラムと、前記ターゲットプログラムで用いられる複数の変数にそれぞれアドレスを割り当てたアドレス定義データと、の入力を受け付ける入力受付ステップと、
前記入力受付ステップで入力されたターゲットプログラムに含まれる各文の各々から定義変数と参照変数とを検出し、前記文毎に前記文の行番号と前記定義変数のアドレスと前記参照変数のアドレスとを対応付けたアドレス間定義−参照データを生成するアドレス間定義−参照データ生成ステップと、
前記アドレス間定義−参照データに基づき、前記定義変数のアドレスと、前記定義変数を含む文の行番号と、前記定義変数と同一アドレスの参照変数を含む文の行番号とを対応付けたアドレス依存データを生成するアドレス依存データ生成ステップと、
前記ターゲットプログラムから制御文と、前記制御文の実行結果に依存して実行される制御対象文とを検出し、前記制御文の行番号と、前記制御対象文の行番号とを対応付けた制御依存データを生成する制御依存データ生成ステップと、
前記ターゲットプログラムにおける所望の行番号をスライス基準として指定するスライス基準指定ステップと、
前記スライス基準として指定された行番号の文を始点とし、前記制御依存データおよび前記アドレス依存データに基づいて到達する文の集合を前記ターゲットプログラムからスライスとして抽出するスライス抽出ステップと、
を備える。
【０００７】
本発明の一態様としての解析プログラムは、上記プログラム解析方法の各ステップをコンピュータに実行させるための命令コード群を備えたことを特徴とする。
【発明の効果】
【０００８】
本発明により、ターゲットプログラムから互いに依存関係のある文の集合を正しく抽出することを可能とした
【発明を実施するための最良の形態】
【０００９】
まず、以降の説明において使用する、プログラムの構文に関する用語について定義する。この用語の定義はJIS X3010に準拠している。
【００１０】
“式(expression)”とは演算子及びオペランドの列のことである。
【００１１】
“式文(expression-statement)”とは式(expresstion)にセミコロン(;)を付加したものか、セミコロン(;)のみのことである。
【００１２】
“宣言(declaration)”とは変数などの識別子の属性を指定する構文のことである。
【００１３】
“文(statement)”とは、実行すべき動作を規定する単位のことでありfor文,while文などの繰り返し文、switch文などの選択文、case文などのラベル付き文、式文、複数の文もしくは複数の宣言(declaration)を１つにまとめた複合文、goto文、return文などの分岐文がある。繰り返し文、選択文、ラベル付き文、分岐文をまとめて制御文と称することもある。
【００１４】
以下、本発明者らが本発明を着想する以前から知っていた従来のプログラムスライシングについて説明する。
【００１５】
図２０は、従来におけるプログラム解析装置の構成を示す。
【００１６】
構文解析部１１０は、テキストで記述されたターゲットプログラム１００を読み込み、構文解析を行う。構文解析では、与えられた文字列を構文規則にしたがって解析し、対象のプログラム言語（たとえばＣ言語）として許される構造をもつものかどうかを同定することによって行われる。より詳細には、まずターゲットプログラム１００を読み込み”＝”や数値などのトークンに分解する字句解析を行い、次にトークンの並びがプログラムの文法に適合しているかを評価する。最後に構文木と呼ばれるラベル付き有向グラフを出力する。構文木の節点には演算子、葉にはオペランドが対応づけられる。
【００１７】
例えばターゲットプログラム１００として以下を仮定する。
［０−１］
L1: a = 10;
L2: b = a * 2;
L3: if( b > 10 ){
L4:   c = a;
L5:   d = b;
}
【００１８】
この場合、構文木のテキスト表記は以下のようになる。また、この構文木の構造は図２３のようになる。ここで［０−１］のターゲットプログラムにおいて、L1-L5は行番号とする。なお、構文木の作成プロセスの詳細については後述する。
［０−２］
L01:<stmts>
L02:  <stmt num=”1” type=”exp”>
L03:    <node op=”=”><l>a</l><r>10</r></node>
L04:  </stmt>
L05:  <stmt num=”2” type=”exp”>
L06:    <node op=”=”><l>b</l><r><node op=”*”><l>a</l><r>2</r></node></r></node>
L07:  </stmt>
L08:  <stmt num=”3” type=”if”>
L09:     <node>
L10:       <l><node op=">"><l>b</l><r>10</r></node></l>
L11:       <r><stmts>
L12:        <stmt num="4" type="exp"><node op="="><l>c</l><r>a</r></node></stmt>
L13:        <stmt num="5" type="exp"><node op="="><l>d</l><r>b</r></node></stmt>
L14:      </stmts></r>
L15:  </stmt>
L16:</stmts>
【００１９】
変数定義−参照関係解析部１１１は構文木から式を一行ずつ読み込み、代入演算子の左辺にある変数を定義変数（定義部）として抽出し、また代入演算子の右辺にある変数を参照変数（参照部）として抽出し、行番号に関連づけて、定義変数と参照変数との対応関係を表した変数間定義−参照テーブル１１２を生成する。上記［０−２］の構文木に基づいて生成される変数間定義−参照テーブル１１２の例を図２１に示す。
【００２０】
変数依存関係解析部１１３は、変数間定義−参照テーブル１１２に基づき変数依存テーブル１１４を生成する。まず変数間定義−参照テーブル１１２で定義されている定義変数を取り出し、取り出した定義変数に対応する行番号を記憶する、次にその定義変数の名に一致する参照変数を検出し、検出した参照変数に対応する行番号を記憶する。そしてこの定義変数の行番号と、この定義変数名と、検出した参照変数の行番号とを１組にして変数依存関係データとし、変数依存テーブル１１４に保存する。ここでは変数依存関係をＤＤという接頭語を用いて表記する。例えば変数aが行番号１で定義され、行番号２で参照されていたとすると、変数依存関係は、
DD(1,a,2)
と表記される。
【００２１】
ここでＤＤ（ｓ、ｗ、ｔ）は、あるアドレスｗが存在して、行番号ｓにおけるアドレスｗの定義が、アドレスｗを参照している行番号ｔに到達していることを示す。
【００２２】
上記［０−１］のターゲットプログラムに対する変数依存テーブル１１４は以下のようになる。
［０−３］
DD(1,a,2)
DD(1,a,4)
DD(2,b,3)
DD(2,b,5)
【００２３】
制御依存関係解析部１１５は、構文解析部１１０で生成された構文木に基づき、制御依存テーブル１１６を生成する。構文木が上記［０−２］のようにテキスト表記で与えられたとすると、まずこのテキストを読み込み、stmtタグの属性typeが”if”等の制御文である式を取り出す。ここではＬ０８からＬ１５までがこれに相当する。またこのstmtタグの行番号を記憶する。次にＬ０８〜Ｌ１５に含まれる行番号を取り出し記憶する。具体的にstmtタグの後にnum属性がある行番号を記憶する。そして、上記制御文に対応するstmtタグの行番号を、Ｌ０８〜Ｌ１５から取り出された各行番号とそれぞれ組み合わせて行番号のペアを生成する。ここでは式３と式４のペア、式３と式５のペアが生成される。各ペアの関係は制御依存関係として、接頭語ＣＤをつけて表記される。各ペアについてそれぞれ生成された制御依存関係のデータは、制御依存テーブル１１６に保存される。
【００２４】
例えば上記［０−１］のターゲットプログラムに対する制御依存テーブル１１６は以下のようになる。ここで、ＣＤ（ｓ、ｔ）は、行番号ｓが制御文であり、その分岐節が行番号ｔを含むことを表す。
［０−４］
CD(3,4)
CD(3,5)
【００２５】
スライス処理部１１８は、以上のように生成された変数依存テーブル１１４及び制御依存テーブル１１６と、別途、スライス基準入力手段１１７から与えられるスライス基準とに基づきプログラムスライシングを行い、スライス基準に依存関係のあるプログラム断片（部分プログラムあるいはスライス）１１９を抽出し、出力する。スライス基準は、たとえば（１）注目する行番号（すなわち注目する文）、または（２）注目する行番号とその行番号の文に含まれる注目変数との組、によって表される。プログラム断片（スライス）は、スライス基準に対して、変数依存テーブル１１４と制御依存テーブル１１６に基づき、依存関係のある全ての文（行番号）を抽出することで求まる。
【００２６】
たとえば、スライス基準としての式５（Ｌ５）に対するスライスは、ＣＤ（３，５）によって３行目が依存し、次にＤＤ（２，ｂ，３）によって２行目が依存し、ＤＤ（1,a,２）によって１行目が依存していることが分かる。よってスライス基準に依存関係のある全ての文（プログラム断片）を抽出すると以下のようになる。
［０−５］
L1: a = 10;
L2: b = a * 2;
L3: if( b > 10 ){
L5:   d = b;
}
【００２７】
ここで、式間の全ての依存関係を抽出する方法として可到達行列を求める方法を用いることもできる。例えば［０−１］のターゲットプログラムに対する変数依存テーブル１１４及び制御依存テーブル１１６を行列Ａとして表記すると、行列Ａは
【数１】
2009237762.tif 000003
のように表現される。この行列Ａの可到達行列Ｂは単位行列をＩとすると
Ｂ＝（Ｉ＋Ａ）６
のように求まる。式５に対するプログラム断片（スライス）は可到達行列Ｂの５行目の依存関係を抽出することで得られる。
【００２８】
以上に説明したような従来のプログラムスライシングの技術については非特許文献１及び非特許文献２で詳述されている。
【００２９】
しかしながら、このような従来の方法では、背景技術の欄に述べたように、プログラム断片（スライス）を適正に抽出できないケースがあった。
【００３０】
すなわち、ある変数と、別の変数があり、これらの変数が同一のアドレスを指す場合、従来の方法では、変数名に着目して処理を行うため、これらの変数を依存関係がないとして扱ってしまっていた。また共用体の変数などが含まれたプログラムでは、共用体として宣言された変数（メンバ変数）がそれぞれ別個のものとして扱われてしまうため、プログラム断片を正しく抽出できなかった。その他、配列またはポインタなどを含むプログラムに対しても正しくプログラム断片を抽出できなかった。
【００３１】
本発明の実施の形態は、このような場合においても、プログラム断片を正しく抽出することを可能にするものである。
【００３２】
以下、図面を参照しながら、本発明の実施の形態について詳細に説明する。
【実施例１】
【００３３】
図２は、第一の実施例に係るプログラム解析装置の構成を示すハードウェアブロック図である。このプログラム解析装置は、データおよびプログラム（本実施例に係る解析プログラム、および解析対象となるターゲットプログラム）を保存する記憶装置１６、データを一時的に記憶するメインメモリ１５、記憶装置１６から本実施例に係る解析プログラムを読み出しメインメモリ１５に展開して実行するＣＰＵ１１、制御の指示及びデータの入力を行うキーボード１２およびマウス１３、データの出力を行うディスプレイ１４、を備え、これらの各要素がバス１７を介して接続されている。本実施例に係る解析プログラムはＣＤ−ＲＯＭ、ＣＤ−Ｒ、リムーバブルディスク等のコンピュータ読み取り可能な記録媒体に記録されて、ＣＰＵ１１によって読み出され実行されてもよい。上記本実施例に係る解析プログラムをＣＰＵ１１が実行することにより得られる各機能をブロックにより表現し、各機能により得られるデータ（テーブル）の入出力関係を各ブロック間で示したのが図１である。すなわち、図１は第一の実施例に係るプログラム解析装置の機能ブロック図である。
【００３４】
図１において、変数−アドレス解析部１００１、構文解析部１０１２、アドレス定義−参照関係解析部１００３、アドレス依存関係解析部１００５、制御依存関係解析部１０６６、スライス抽出部１０１０は、本実施例に係わる解析プログラムをCPUに実行させることにより得られる各機能に相当する。図中のターゲットプログラム１０００は、解析対象となるターゲットプログラムであり、たとえばキーボード１２およびマウス１３から文字列を入力することで作成されることができる。変数−アドレス対応テーブル１００２、構文木１０１３、アドレス間定義−参照テーブル１００４、アドレス依存テーブル１００７、制御依存テーブル１００８、プログラム断片（部分プログラムあるいはスライスとも称される。以降プログラム断片に統一する）１０１１は、上記各機能により生成されるデータまたはテーブルに相当する。スライス基準入力手段１００９は、たとえばキーボード１２またはマウス１３に相当する。なお、ターゲットプログラム１０００はたとえば図３に示されるような、ＣＰＵ２１、ＲＡＭ２２、表示部２３、記憶装置２４がバス２５を介して接続されたコンピュータシステムで実行されることができる。この場合、記憶装置２４に保存されたターゲットプログラム１０００をＣＰＵ２１が読み出して実行し、ＲＡＭ２２がプログラム実行中の途中データを一時的に格納する。プログラム実行結果は表示部２３において表示される。
【００３５】
図１において、本プログラム解析装置は、ターゲットプログラム１０００を記憶装置１６（図２参照）から読み出し、変数−アドレス解析部１００１と構文解析部１０１２に入力する。ターゲットプログラム１０００はＣ言語などのプログラム言語の文法に沿って記述されている。
【００３６】
変数−アドレス解析部１００１は、入力されたターゲットプログラム１０００を用いて、変数名と絶対アドレスとを対応付けた変換−アドレス対応テーブル（マップ）１００２を作成する。絶対アドレスとは、ターゲットプログラム１０００が実際に実行される時に変数が一時的に格納されるメモリの番地のことである。
【００３７】
本例では、下記のように、絶対アドレスを用いてある変数と別の変数とが同一のアドレスを指すターゲットプログラム１０００が入力されるとする。変数aと変数bとがそれぞれ同じアドレスを示す。
［１−１］
L1: #pragma ADDRESS a 0x0001
L2: #pragma ADDRESS b 0x0001
L3: #pragma ADDRESS c 0x0002
L4: #pragma ADDRESS d 0x0003
L5: a = 10;
L6: if( b > 10 ){
L7:   c = a;
L8:   d = b;
}
【００３８】
変数−アドレス解析部１００１ではまずターゲットプログラム１０００を１行ずつ読み込み、行の先頭に#pragmaが含まれる行を取り出す。先頭に#pragmaが含まれる行の集合はたとえばアドレス定義データに相当する。
【００３９】
次に取り出したそれぞれの行をスペース文字でトークンに分割し、２番目のトークンがADDRESSである行を検出する。そして、各検出した行について、３番目のトークンを変数名、４番目のトークンを絶対アドレスとして変数−アドレス対応テーブル１００２に追加する。上記［１−１］のターゲットプログラムから生成された変数−アドレス対応テーブル１００２を以下に示す。
［１−２］
a 0x0001
b 0x0001
c 0x0002
d 0x0003
【００４０】
構文解析部１０１２は、ターゲットプログラム１０００を読み込み、絶対アドレスの指定を行っている行以外について、構文解析を行うことにより、ターゲットプログラム１０００の構文を木構造で表した構文木１０１３を作成する。作成された構文木１０１３はメインメモリ１５に一時的に保存される。ここで構文解析は、文字列を構文規則にしたがって解析し、対象プログラム言語（たとえばＣ言語）として許される構造をもつものかどうかを同定することによって行われる。
【００４１】
例えば、
０１：main(){
０２： int a;
０３： a = 1;
０４：}
のプログラムの構文木は図４のようになる。
【００４２】
より詳細に、構文解析はでまずターゲットプログラム１０００を読み込み、“＝”や数値などのトークンに分解する字句解析を行い、次にトークンの並びがプログラムの文法に適合しているかを評価する。最後に構文木と呼ばれるラベル付き有向グラフを出力する。構文木は、XML形式（テキスト表記）で表現することもできる。［１−１］のターゲットプログラムから作成される構文木のテキスト表記を以下に示す。またこの構文木の構造を図５に示す。
［１−３］
L01:<stmts>
L02:  <stmt num=”5” type=”exp”>
L03:    <node op=”=”><l>a</l><r>10</r></node>
L04:  </stmt>
L08:  <stmt num=”6” type=”if”>
L09:     <node>
L10:       <l><node op=”>”><l>b</l><r>10</r></node></l>
L11:       <r><stmts>
L12:        <stmt num=”7” type=”exp”><node op=”=”><l>c</l><r>a</r></node></stmt>
L13:        <stmt num=”8” type=”exp”><node op=”=”><l>d</l><r>b</r></node></stmt>
L14:      </stmts></r>
L15:  </stmt>
L16:</stmts>
【００４３】
上記において、複数の文は<stmts>タグで表記している。またそれぞれの文を<stmt>タグで表記している。また対応する先頭の行番号はnum属性で表記している。また文の種類がif,for,whileなどの繰り返し文、選択文、ラベル付き文、式文、複合文、分岐文の場合はtype属性として文の種類を表記している。文が式文の場合はexp属性をつけている。式の中は２分木として表記され、節を<node>タグで表記し、節が属するトークンをop属性で表記している。また節の左の枝を<l>タグ、節の右の枝を<r>タグで表記している。
【００４４】
アドレス定義−参照関係解析部１００３は、構文木１０１３と変数−アドレス対応テーブル１００２とを読み込み、構文木１０１３に含まれる各文について、行番号と、定義変数のアドレスと、参照変数のアドレスとをそれぞれ対応付けた、アドレス間定義―参照テーブル１００４を生成する。上記［１−３］の構文木と、［１−２］の変数−アドレス対応テーブル１００２から生成されたアドレス間定義―参照テーブル１００４を図７に示す。１列目は行番号を表し、［１−３］の<stmt>タグのnum属性に対応する。２列目は定義変数のアドレス、３行目は参照変数のアドレスを表す。
【００４５】
図６は、第一の実施例に係るアドレス定義−参照関係解析部１００３の動作フローを示すフローチャートである。
【００４６】
まず構文木から１文を取り出す（ＳＴ１００）。構文木において図４に示すように文の先頭の根に式番号をつけ、式番号に一致する根以下の情報を抽出することによって１文を取り出すことができる。
【００４７】
次に上記１文から定義変数を取り出す（ＳＴ１０１）。ここで定義変数とは文中に等号記号（代入演算記号（(<node>タグのop属性が”=”)）を持ち、その式が実行された後の値を代入する先の変数（通常等号記号の左側にある変数）を指す。例えば［１−１］の式７（Ｌ７）では変数ｃが定義変数となる。
【００４８】
次に上記１文から参照変数を取り出す（ＳＴ１０２）。参照変数は文が実行されるときに値が呼び出される変数である。例えば［１−１］の式７（Ｌ７）では変数ａが参照変数であり、式８（Ｌ８）では変数ｂが参照変数となる。また<stmt>タグのタイプが”if”である場合は、その下の<node>タグの<l>タグを読み込み、その下の変数名を参照変数とする。たとえば式６（Ｌ６）では変数ｂが参照変数である。
【００４９】
次に定義変数および参照変数をそれぞれアドレスに変換する（ＳＴ１０３）。
【００５０】
次にアドレス間定義−参照テーブル１００４に、上記文の行番号と、定義変数のアドレスと、参照変数のアドレスとの対応関係を登録する（ＳＴ１０４）。
【００５１】
次に全ての文が取り出されたか否かを判定する（ＳＴ１０５）。全ての文が取り出されていない場合は（ＮＯ）ＳＴ１００に戻り、全ての文が取り出されている場合は（ＹＥＳ）処理を終了する。
【００５２】
アドレス依存関係解析部１００５は、アドレス間定義―参照テーブル１００４を用いて、定義変数毎に、定義変数のアドレスと、当該定義変数を含む文の行番号と、当該定義変数と同一のアドレスをもつ参照変数を含む文の行番号とを対応付けたアドレス依存アドレス依存テーブル（アドレス依存データ）１００７を作成する。図７のアドレス間定義―参照テーブル１００４から作成したアドレス依存テーブル１００７は以下のようになる。
［１−４］
DD(5,0x0001,6)
DD(5,0x0001,8)
DD(5,0x0001,7)
【００５３】
ここでＤＤ（ｓ、ｗ、ｔ）は、あるアドレスｗが存在して、行番号ｓにおけるアドレスｗの定義が、アドレスｗを参照している行番号ｔに到達していることを示す。
【００５４】
図８は、第一の実施例に係るアドレス依存関係解析部１００５の動作フローを示すフローチャートである。
【００５５】
まずアドレス間定義―参照テーブル１００４から定義アドレス（定義変数のアドレス）と、その定義アドレスが含まれる行番号とを取得する（ＳＴ２００）。
【００５６】
次にアドレス間定義―参照テーブル１００４から、取得した定義アドレスに一致する参照アドレス（参照変数のアドレス）を検出し、検出した参照アドレスの行番号を取得する（ＳＴ２０１）。
【００５７】
次に、取得した定義アドレスの行番号と、取得した定義アドレスと、検出した参照アドレスの行番号とを１組として、アドレス依存テーブル１００７に登録する（ＳＴ２０２）。
【００５８】
次に、ＳＴ２００で取得した定義アドレスに一致する全ての参照アドレスを検出したか否かを判定する（ＳＴ２０３）。
【００５９】
まだ検出していない参照アドレスがある場合は（ＳＴ２０３のＮＯ）ＳＴ２００に戻り、すべての参照アドレスを検出した場合は（ＹＥＳ）、また取得していない定義アドレスがあるかどうかを判定する（ＳＴ２０４）。まだ取得していない定義アドレスがある場合は（ＮＯ）ＳＴ２００に戻り、もしすべての定義アドレスを取得した場合は（ＹＥＳ）処理を終了する。
【００６０】
制御依存解析部１００６は、構文木１０１３に基づき、制御文と、当該制御文の実行結果に依存して実行される制御対象文とを検出し、制御文の行番号と、制御対象文の行番号とを対応付けた制御依存テーブル（制御依存データ）１００８を作成する。上述した［１−３］の構文木から作成した制御依存テーブル１００８は以下のようになる。
CD(6,7)
CD(6,8)
【００６１】
ここで、ＣＤ（ｓ、ｔ）は、行番号ｓが制御文であり、その分岐節が行番号ｔを含むことを表す。
【００６２】
図９は、第一の実施例に基づく制御依存関係解析部１００６の動作フローを示すフローチャートである。
【００６３】
まず構文木１０１３から制御文を取り出す（ＳＴ３００）。制御文とは例えばＣ言語の場合if文、switch文などの条件分岐、for文、while文、do-while文などの繰り返し文を指す。構文木では取り出した式の内部に制御文を示すキーワードが存在すれば、それは制御文であると判断できる。［１−１］のターゲットプログラムの場合は、if( b > 10 )が制御文に相当する。
【００６４】
次に制御文に応じて実行される制御対象の文の行番号を取り出す（ＳＴ３０１）。
【００６５】
次に制御文の行番号と、制御対象の文の行番号とのペアを制御依存テーブル１００８に追加する（ＳＴ３０２）。例えば［１−１］のターゲットプログラムの場合は、Ｌ６とＬ７のペア、Ｌ６とＬ８のペアが得られる。
【００６６】
次に制御文を全て取得したかどうかを判定する（ＳＴ３０３）。まだ取得していない制御文がある場合は（ＮＯ）ＳＴ３００に戻り、全ての制御文を取得した場合は（ＹＥＳ）、処理を終了する。
【００６７】
スライス基準入力手段１００９は、スライス基準を入力する。スライス基準は、たとえば注目する行番号（すなわち注目する文）である。注目する行番号に加えて、その行番号の文に含まれる注目変数の指定を含んでも良い。スライス基準入力手段１００９は例えばキーボードの場合、キー入力により行番号を入力しても良いし、ファイル入力手段として機能する場合、ファイルなどによって行番号を入力しても良い。またマウスの押下げ回数などによってスライス基準を入力することもできる。スライス基準入力手段１００９は、このような外部から入力されたスライス基準をスライス抽出部１０１０に出力する。本実施例に係るプログラム解析装置は、ターゲットプログラムにおける任意の行番号を、スライス基準として指定するスライス基準指定手段を含んでもよい。
【００６８】
スライス抽出部１０１０は、アドレス依存テーブル１００７および制御依存テーブル１００８を用いて、入力されたスライス基準に対する全ての依存関係のある文（行）を抽出することでプログラム断片１０１１を取得する。すなわち、スライス基準に示される行番号の文を始点とし、アドレス依存テーブル１００７および制御依存テーブル１００８に基づいてスライス基準から到達するすべての文の集合をプログラム断片１０１１として抽出する。なお、アドレス依存テーブル１００７および制御依存テーブル１００８の可到達行列を計算し、可到達行列を利用して、スライス抽出を行うこともできる。
【００６９】
本例におけるアドレス依存テーブル１００７と制御依存テーブル１００８に基づき、スライス基準としての式８（行番号Ｌ８）に対するプログラム断片を抽出すると
L5: a = 10;
L6: if( b > 10 ){
L8:   d = b;
}
となる。つまりCD(6,8)によって６行目が依存し、次にDD(5,0x0001,6)によって５行目が依存していることが分かる。このようにして、式８（Ｌ８）に対する依存関係を正しく抽出することができる。本例では、スライシングとしてバックワードスライシングを示したが、フォワードスライシングを行ってもよく、またはこれらの両方のスライシングを行い、両者の和集合をプログラム断片として抽出してもよい。
【００７０】
ここで、上記ターゲットプログラム［１−１］に対して、前述した従来技術を用いた場合は、本実施例のように依存関係のある文の集合を正しく抽出することができない。以下これを示す。
【００７１】
図２０に示した従来技術を用いた場合、変数間定義−参照テーブル１１２は図２２に示すようになる。
【００７２】
また、変数依存テーブル１１４及び制御依存テーブル１１６は以下のようになる。
DD(5,a,7)
CD(6,7)
CD(6,8)
【００７３】
以上から式８（Ｌ８）に対するプログラム断片を抽出すると
L6: if( b > 10 ){
L8:   d = b;
}
となる。よって、従来技術では、上記［１−１］のターゲットプログラムに対して、正しく依存関係を抽出できないことが分かる。
【００７４】
図１０は、第一の実施例に係るプログラム解析方法の一例を説明するフローチャートである。
【００７５】
まずターゲットとなるプログラム１０００（ファイル）を読み込む（ＳＴ４００）。
【００７６】
次に読み込んだターゲットプログラム１０００において、プラグマ（pragma）文などの絶対アドレスの指定を行っている行の構文を解析することにより変数−アドレス対応テーブル１００２を生成する（ＳＴ４０１）。
【００７７】
次にターゲットプログラム１０００において絶対アドレスの指定を行っている以外の部分の構文解析を行うことにより構文木１０１３を作成する（ＳＴ４０２）。
【００７８】
次に、構文木１０１３と変数−アドレス対応テーブル１００２からアドレス間定義−参照テーブル１００４を作成する（ＳＴ４０３）。
【００７９】
次に、アドレス間定義−参照テーブル１００４からアドレス依存テーブル１００７を作成する（ＳＴ４０４）。
【００８０】
次に、構文木１０１３から制御依存テーブル１００８を作成する（ＳＴ４０５）。
【００８１】
次にスライス基準を読み込み（ＳＴ４０６）、スライス抽出を行うことによりプログラム断片を作成する（ＳＴ４０７）。
【００８２】
以上に示した各ステップの順序はあくまで一例であり、本発明はこの順序に限定されない。たとえばＳＴ４０４とＳＴ４０５の順序が逆でもよく、この場合も、本発明の効果は損なわれない。
【００８３】
以上のように、本実施例によれば、アドレスの依存関係に基づきスライシングを行うため、依存関係のある文を正しく抽出できる。また、アドレスの依存関係だけを見て処理をすればいいので処理を単純化でき、よって処理が高速化される。また、複数の構文が組み合わさったときにも対応できる。
【実施例２】
【００８４】
本実施例では、第一の実施例のプログラム解析装置を用いて、共用体を持つターゲットプログラムをスライシングする例を示す。以下に共用体をもつターゲットプログラム１０００の例を示す。data1が共用体の変数であり、data1.aおよびdata1.b[…]は共用体のメンバ変数に相当する。
［２−１］
L1:#pragma ADDRESS data1 0x0001
L2:#pragma ADDRESS b 0x0002
L3:#pragma ADDRESS c 0x0003
L4:#pragma ADDRESS d 0x0004
L5:   union data { 
L6:     short a, char b[2] } data1;
L7: data1.a = 256;
L8: b = data1.b[1];
L9: if( b > 0 ){
L10:   c = data1.b[b];
L11:   d = b;
L12: }
【００８５】
まず構文解析部１０１２において［２−１］のターゲットプログラムから構文木１０１３を作成する。作成された構文木１０１３を図１１に、またこの構文木のテキスト表記を以下に示す。
［２−２］
L01:<stmts>
L02:  <stmt num=”7” type=”exp”>
L03:    <node op=”=”><l>data1.a</l><r>10</r></node>
L04:  </stmt>
L05:  <stmt num=”8” type=”exp”>
L06:    <node op=”=”><l>b</l><r><node><l>data1.b</l><r>1</r></node></r></node>
L07:  </stmt>
L08:  <stmt num=”9” type=”if”>
L09:     <node>
L10:       <l><node op=”>”><l>b</l><r>10</r></node></l>
L11:       <r><stmts>
L12:        <stmt num=”10” type=”exp”>
L13:          <node op=”=”><l>c</l><r><node><l>data1.b</l><r>b</r></node></r></node></stmt>
L14:        <stmt num=”11” type=”exp”><node op=”=”><l>d</l><r>b</r></node></stmt>
L15:      </stmts></r>
L16:  </stmt>
L17:</stmts>
【００８６】
次に変数−アドレス解析部１００１において［２−１］のターゲットプログラムから変数−アドレス対応テーブル１００２を作成する。作成した変数−アドレス対応テーブル１００２を以下に示す。
［２−３］
data1 0x0001
b     0x0002
c     0x0003
d     0x0004
【００８７】
次に、アドレス定義−参照関係解析部１００３において、［２−３］の変数−アドレス対応テーブル１００２と、［２−２］の構文木１１００から、アドレス間定義−参照テーブル１００４を作成する。作成したアドレス間定義−参照テーブル１００４を図１２に示す。data1.a,data1.b[1]などの共用体のメンバ変数(変数名にdata1（共用体の変数）が含まれる変数)については、全てdata１の先頭アドレス0x0001に変換する。共用体とは無関係の変数については実施例１と同様にして処理を行えばよい。
【００８８】
次にアドレス依存関係解析部１００５においてアドレス間定義−参照テーブル１００４からアドレス依存テーブル１００７を作成し、また、制御依存関係解析部１００６において構文木１０１３から制御依存テーブル１００８を作成する。作成したアドレス依存テーブル１００７および制御依存テーブル１００８をそれぞれ［２−４］および［２−５］として以下に示す。
［２−４］
DD(7,0x0001,8)
DD(7,0x0001,10)
DD(8,0x0002,9)
DD(8,0x0002,11)
［２−５］
CD(9,10)
CD(9,11)
【００８９】
次にスライス抽出部１０１０において、このアドレス依存テーブル１００７と制御依存テーブル１００８に基づき、たとえばスライス基準としての式１１（Ｌ１１）に対するプログラム断片１０１１を抽出すると
L7: data1.a = 256;
L8: b = data1.b[1];
L9: if( b > 0 ){
L11:   d = b;
}
となる。よって、共用体の変数を含むターゲットプログラムであっても、依存関係のある文（プログラム断片）を正しく抽出することができる。
【実施例３】
【００９０】
図１３は、第三の実施例に係るプログラム解析装置の機能ブロック図である。図１３のプログラム解析装置は、第一の実施例と同様に、図２に示したようなシステムにおけるＣＰＵに本実施例に係わる解析プログラムを実行させることによって実現される。以下、ポインタを含むターゲットプログラムを例にして、図１３のプログラム解析装置の動作について説明する。
【００９１】
図１３のプログラム解析装置に、記憶装置１６から解析対象となるターゲットプログラム１０００が読み込まれる。本実施例ではポインタをもつターゲットプログラムが入力され、その一例を以下に示す。なお各変数の定義文は、表記の簡単のため省略している。なお、変数ｂはポインタ変数である。
［３−１］
L００：#pragma ADDRESS a 0x0001
L０１：#pragma ADDRESS b 0x0002
L０２：#pragma ADDRESS c 0x0003
L０３：#pragma ADDRESS d 0x0004
L０４：#pragma ADDRESS e 0x0005
L０５：a = 10;                       
L０６：b = &a;                       
L０７：c =*b * 2;                   
L０８：if( c > 10 ){                 
L０９：  d = a;                     
L１０：  e = *b;                     
L１１：}
【００９２】
変数−アドレス解析部１００１は、入力されたターゲットプログラム１０００から、変数−アドレス対応テーブル１００２を作成する。より詳細には、変数−アドレス解析部１００１は、第一の実施例と同様に、文の先頭が#pragmaではじまる各行について、その行に含まれる変数名とアドレスとのペアを取り出し、変数−アドレス対応テーブル１００２に格納する。作成された変数−アドレス対応テーブル１００２は記憶装置１６に保存するか、一時的にメインメモリ１５に記憶される。
【００９３】
構文解析部１０１２は、入力されたターゲットプログラム１０００を読み込み、構文解析を行うことにより構文木１０１３を作成する。［３−１］のターゲットプログラムから作成される構文木１０１３の構造を図１４に、またこの構文木のテキスト表記を以下に示す。
［３−２］
L01:<stmts>
L02:  <stmt num=”5” type=”exp”>
L03:    <node op=”=”><l>a</l><r>10</r></node>
L04:  </stmt>
L02:  <stmt num=”6” type=”exp”>
L03:    <node op=”=”><l>b</l><r><node><l>&</l><r>a</r></node></r></node>
L04:  </stmt>
L02:  <stmt num=”7” type=”exp”>
L03:    <node op=”=”><l>c</l><r><node op=”*”><l>b</l><r>2</r></node></r></node>
L04:  </stmt>
L08:  <stmt num=”8” type=”if”>
L09:     <node>
L10:       <l><node op=”>”><l>c</l><r>10</r></node></l>
L11:       <r><stmts>
L12:        <stmt num=”9” type=”exp”><node op=”=”><l>d</l><r>a</r></node></stmt>
L14:        <stmt num=”10” type=”exp”><node op=”=”><l>e</l><r>b</r></node></stmt>
L15:      </stmts></r>
L16:  </stmt>
L17:</stmts>
【００９４】
ポインタ解析部１０１４は、ターゲットプログラム１０００、変数−アドレス対応テーブル１００２及び構文木１０１３を読み込み、ポインタ解析を行うことにより、アドレス間参照関係データ１０１５を生成する。ポインタ解析についてはたとえばDasの方法（Manuvir Das, Unification-based Pointer Analysis with Directional Assignment）などが知られている。
【００９５】
以下にポインタ解析部１０１４の動作を示す。
【００９６】
まず構文木１０１３から、アドレスを用いた演算が行われている文を取り出す。［３−１］の場合、アドレスを用いた演算が行われているのは式６（Ｌ０６）である。
【００９７】
次にこの文において、呼び出される変数（等号記号の右側にある変数）を取り出し、変数−アドレス対応テーブル１００２からこの変数に対応するアドレスを取得する。また、アドレス代入先の変数（等号記号の左側にある変数）を取り出し、変数−アドレス対応テーブル１００２からその変数に対応するアドレスを取得する。そして、これらのアドレスの依存関係を、たとえば“（代入先の変数に対応するアドレス）→（呼び出される変数に対応するアドレス）”のように表し、アドレス間参照関係データ１０１５として保存する。
【００９８】
［３−１］のターゲットプログラムの場合、式６（L06）に対して、アドレス間参照関係データ１０１５として、
0x0002 -> 0x0001
が得られる。ここで右矢印（→）は０ｘ０００２番地が指定された場合は０ｘ０００１番地に置き換えるという規則を示す。
【００９９】
アドレス定義−参照関係解析部１００３は、構文木１０１３、変数−アドレス対応テーブル１００２およびアドレス間参照関係データ１０１５を読み込みアドレス間定義―参照テーブル１００４を作成する。作成されたアドレス間定義―参照テーブル１００４はメインメモリ１５に一時的に記憶される。以下、図６を参照して、アドレス定義−参照テーブル１００４の作成手順を説明する。
【０１００】
まず構文木１０１３から１文を取り出す（ＳＴ１００）。
【０１０１】
次に抽出した１文から定義変数を取り出す（ＳＴ１０１）。例えば［３−１］の式７（Ｌ０７行目）では変数ｃが定義変数となる。ただし式６（Ｌ０６行目）のｂはアドレスが代入されている（値が代入されているのではない）ため定義変数には該当しない。
【０１０２】
次にこの一文から参照変数を取り出す（ＳＴ１０２）。例えば［３−１］の式７（Ｌ０７行目）では変数ｂが参照変数であり、式８（Ｌ０８行目）は式ｃが参照変数となる。ただし、式６（Ｌ０６行目）の変数ａはアドレスが呼び出されている（値が呼び出されているのではない）ため参照変数ではない。
【０１０３】
次に変数−アドレス対応テーブル１００２から定義変数および参照変数に対応するアドレスを読み込み（ＳＴ１０３）、アドレス間定義−参照テーブル１００４に追加する（ＳＴ１０４）。この際、アドレス間参照関係データ１０１５に基づき、“代入先の変数に対応するアドレス”があるときは、そのアドレスを“呼び出される変数に対応するアドレス”に変換する。
【０１０４】
次に構文木の全ての文が処理されたかを判定し（ＳＴ１０５）、全ての文が処理されたら（ＹＥＳ）、処理を終了する。
【０１０５】
以上の処理により作成されたアドレス間定義―参照テーブル１００４は以下のようになる
［３−３］
行  定義     参照
L05 0x0001 
L07 0x0003  0x0001
L08          0x0003
L09 0x0004   0x0001
L10 0x0005   0x0001
【０１０６】
次にアドレス依存関係解析部１００５は、アドレス間定義―参照テーブル１００４を読み込み、アドレス依存テーブル１００７を作成する。本処理は第一の実施例と同様、図８に示したフローに従って行えばよい。作成したアドレス依存テーブル１００７はメインメモリ１５に一時的に記憶され、または、記憶装置１６にファイルとして保存してもよい。
【０１０７】
［３−３］のアドレス間定義―参照テーブル１００４から作成されたアドレス依存テーブル１００７を以下に示す。
［３−４］
s     w        T
L05   0x0001    L08 
L05   0x0001    L09
L05   0x0001   L10
L07   0x0003    L08
【０１０８】
次に、制御依存関係解析部１００６は、構文木１０１３に基づき制御依存テーブル１００８を生成する。本処理は第一の実施例と同様、図９に示したフローに従って行う。作成した制御依存テーブル１００８はメインメモリ１５に一時的に記憶され、または、記憶装置１６にファイルとして保存してもよい。
【０１０９】
［３−１］のターゲットプログラムの場合、Ｌ０８とＬ０９、Ｌ０８とＬ１０に制御依存関係が存在するため、以下の制御依存テーブル１００８が得られる。
CD(8,9)
CD(8,10)
【０１１０】
なお、第一の実施例で述べたように、ＣＤ（ｓ、ｔ）は、行番号ｓが制御文であり、その分岐節が行番号ｔを含むことを表す。
【０１１１】
次にスライス基準入力手段１００９がスライス基準を読み込む。スライス基準は例えば行番号である。
【０１１２】
次にスライス抽出部１０１０が、アドレス依存テーブル１００７と制御依存テーブル１００８とアドレス間参照関係データ１０１５に基づき、スライス基準に依存関係のある全ての文（行）を取り出すことによりプログラム断片（スライス）１０１１を作成する。
【０１１３】
例えば［３−１］のターゲットプログラムの場合、行番号９に対するプログラム断片１０１１は
L06: b = &a;
L07: c = *b * 2;
L08: if( c > 10 ){
L09: e = *b;
}
となる。スライス基準における参照変数bのアドレスは0x0001、アドレス間参照関係データ１０１５は0x0002 -> 0x0001であることから、0x0002 -> 0x0001に対応する式（L06）が、スライス基準に依存関係がある行として抽出されている。
【０１１４】
抽出されたプログラム断片１０１１は表示部１４に表示しても良いし、記憶装置１６に保存しても良い。
【０１１５】
以下、ポインタを含む他のターゲットプログラム例として、［３−５］を示す。変数の定義は表記の簡単のため省略している。変数ａ、変数ｂはポインタ変数である。このターゲットプログラム例を元に本実施例における処理例を示す。
［３−５］
L1:#pragma ADDRESS a 0x0001
L2:#pragma ADDRESS b 0x0003
L3:#pragma ADDRESS c 0x0004
L4:#pragma ADDRESS d 0x0005
L5:#pragma ADDRESS e 0x0006
L6: *a = 10;
L7: *(a+1) = 1;
L8: b = a;
L9: c = *(b+1) * 2;
L10: if( c > 10 ){
L11:   d = *a;
L12:   e = *b;
}
【０１１６】
ポインタ解析部１０１４におけるポインタ解析により式８（Ｌ８）に対応して、アドレス間参照関係データ１０１５として以下が得られる。
［３−６］
0x0003 -> 0x0001
【０１１７】
また、アドレス間定義−参照関係解析部１００３における処理により、図１５に示すアドレス間定義−参照テーブル１００４が得られる。
【０１１８】
また、アドレス依存関係解析部１００５および制御依存関係解析部１００６における処理により、アドレス依存テーブル１００７および制御依存テーブル１００８として以下を得ることができる。
［３−７］
DD(6,0x0001,11)
DD(6,0x0001,12)
DD(7,0x0002,9)
DD(9,0x0004,10)
［３−８］
CD(10,11)
CD(10,12)
【０１１９】
この［３−７］のアドレス依存テーブル１００７と、［３−８］の制御依存テーブル１００８と、［３−６］のアドレス間参照関係データ１０１５から、スライス基準としての式２（Ｌ１２）に対するプログラム断片を抽出すると、以下が得られる。
L6: *a = 10;
L7: *(a+1) = 1;
L9: c = *(b+1) * 2;
L10: if( c > 10 ){
L12:   e = *b;
}
【０１２０】
このように、本実施例によれば、ポインタをもつターゲットプログラムであっても、依存関係のある文を正しく抽出することができる。
【実施例４】
【０１２１】
図１６は、第四の実施例に係るプログラム解析装置の機能ブロック図である。以下では図１に示した第一の実施例に係るプログラム解析装置との差分についてのみ説明し、それ以外については第一の実施例と同様であるため、重複する説明を省略する。
【０１２２】
第一の実施例では、ターゲットプログラム内に、変数とアドレスとの対応の定義したデータ（アドレス定義データ）を記述したが、本実施例では、このアドレス定義データを、変数−アドレス定義ファイル１０１６としてターゲットプログラムとは別個に与え、ターゲットプログラムにはこのアドレス定義データを含めない。変数−アドレス定義ファイル１０１６の一例を以下に示す。
［４−１］
a 0x0001
b 0x0001
c 0x0002
d 0x0003
【０１２３】
マップ構文解析１０１７では、変数−アドレス定義ファイル１０１６から、変数名とアドレスとの対応を解析し、変数−アドレス対応テーブル１００２を作成する。
【０１２４】
例えば［４−１］の変数−アドレス定義ファイル１０１６がテキストファイルとして与えられた場合、マップ構文解析１０１７はファイルを一行ずつ読み込み、スペースで２つの文字列に分割し、左側の文字列を変数、右側の文字列をアドレス値とすることによって変数−アドレス対応テーブル１００２を得る。
【実施例５】
【０１２５】
図１７は、第五の実施例に係るプログラム解析装置の機能ブロック図である。本実施例に係るプログラム解析装置は、配列のインデックスを変数で指定しているターゲットプログラムを解析することを特徴とする。例えば以下のようなＣ言語で記述されたターゲットプログラムが、本プログラム解析装置に入力される。式６（Ｌ６行目）では、配列変数aが定義されている。また式１１（L１１行目）では、配列変数aのインデックスを変数cによって指定し、配列変数aの値に応じて、条件分岐を行っている。
［６−１］
L1:#pragma ADDRESS a 0x0000
L2:#pragma ADDRESS b 0x0003
L3:#pragma ADDRESS c 0x0004
L4:#pragma ADDRESS d 0x0005
L5:#pragma ADDRESS e 0x0006
L6:int a[2],*b;
L7: a[0] = 10;
L8: a[1] = 1;
L9: b = &a[0];
L10: c = 0;
L11: if( a[c] > 10 ){
L12:   d = a[0];
L13:   e = b[0];
}
【０１２６】
構文解析部１０１２は、ターゲットプログラム１０００を読み込み、構文解析を行うことにより、構文木１０１３を作成する。作成した構文木１０１３のテキスト表記を下記に示す。また構文木１０１３の構造を図１８に示す。下記のテキスト表記において、<decl>タグは宣言を表している。
［６−２］
L01:<stmts>
L02:  <decl num=”6”>
L03:    <node>
L04:      <l>int</l>
L05:      <r>
L06:        <node><l>a</l><r>2</r></node><node><l>*</l><r>b</r></node>
L07:      </r>
L08:    </node>
L09:  </decl>
L10:  <stmt num=”7” type=”exp”>
L11:    <node op=”=”><l><node><l>a</l><r>0</r></node></l><r>10</r></node>
L12:  </stmt>
L13:  <stmt num=”8” type=”exp”>
L14:    <node op=”=”><l><node><l>a</l><r>1</r></node></l><r>1</r></node>
L15:  </stmt>
L16:  <stmt num=”9” type=”exp”>
L17:    <node op=”=”>
L18:      <l>b</l>
L19:      <r><node><l>&</l><r><node><l>a</l><r>0</r></node></r></node></r>
L20:    </node>
L21:  </stmt>
L22:  <stmt num=”10” type=”exp”><node op=”=”><l>c</l><r>0</r></node></stmt>
L23:  <stmt num=”11” type=”if”>
L24:     <node>
L25:       <l><node op=”>”><l><node><l>a</l><r>c</r></node></l><r>10</r></node></l>
L26:       <r><stmts>
L27:        <stmt num=”12” type=”exp”>
L28:          <node op=”=”><l>c</l><r><node><l>a</l><r>0</r></node></node></stmt>
L29:        <stmt num=”13” type=”exp”>
L30:          <node op=”=”><l>d</l><r><node><l>b</l><r>0</r></node></r></node></stmt>
L31:      </stmts></r>
L32:  </stmt>
L33:</stmts>
【０１２７】
配列サイズ解析部１０１８は、作成された構文木から宣言された配列変数の配列サイズを取得する。例えば構文木が［６−２］の場合、構文木をL01から順に読み込み、declタグをもつ行を取り出す。ここではL02〜L09が該当する。次にdeclタグの木において、その下の節の右の枝に宣言された変数があるためこれを読み込む。それが節(nodeタグ)であり、さらにその節の下において、右の節が数値、左の節が変数のときは、配列宣言が示されている。よって、右の節の数値2と、左の節の変数ａを読み込むことで、変数aは0-2までのインデクスを持つ配列変数であることが分かる。
【０１２８】
次に変数−アドレス解析部１００１によって変数−アドレス対応テーブル１００２を作成する。以下は［６−１］のターゲットプログラムに対して作成された変数−アドレス対応テーブル１００１である。
［６−３］
a 0x0000
b 0x0003
c 0x0004
d 0x0005
e 0x0006
【０１２９】
次にポインタ解析部１０１４はポインタ解析を行う。まず［６−２］の構文木を読み込み、<decl>タグをもつ行を読み込む。<node>タグに基づき、配列宣言およびポインタ宣言された変数を検出する。ここではL06において、aが配列、bがポインタであることがわかる。次にその変数が代入されている式（行）を特定する。変数aと変数bが含まれている<stmt>タグはL16〜L21であり、その中における<node>タグの属性が”=”から、式９において、配列とポインタ間の代入演算が行われていることが分かる。代入元である<r>タグを読み込むことで、配列aのインデクスが0であることがわかる。また代入先である<l>タグを読み込むことで、代入先の変数がbであることが分かる。次に［６−３］の変数−アドレス対応テーブル１００１に基づき、各変数に対応するアドレスを求める。最終的にアドレス間の依存関係（アドレス間参照関係データ１０１５）は以下のようにもとまる。代入先の変数は定義変数、代入元（呼び出し元）の変数は参照変数として扱われる。
［６−４］
0x0003 -> 0x0000
【０１３０】
次にアドレス定義−参照関係解析部１００３によって、図１９に示すアドレス間定義−参照テーブル１００４を作成する。
【０１３１】
［６−１］のターゲットプログラムの11行目の式では、変数aが参照変数であり、そのインデクスは変数cである。具体的に変数aは配列であり、そのインデックスは0-2が宣言されており、インデックスの指定が変数である。そのインデックスの先頭は、［６−３］の変数−アドレス対応テーブル１００１によって0x0000である。このように参照変数が配列であり配列のインデクスが変数で指定されている場合は、全ての候補となるアドレスをアドレス間定義−参照テーブル１００４に抽出する。ここでは配列変数aのインデクスが0のときの0x0000、インデクスが1のときの0x0001,インデクスが2のときの0x0002が候補となるアドレスである。
【０１３２】
本例では、参照変数が配列である場合を示しているが、定義変数が配列であり当該配列のインデックスが変数でしてされている場合も、同様にしてすべての候補となるアドレスを抽出する。
【０１３３】
また［６−２］の構文木において、Ｌ３０から、変数bについてそのインデクスは0であることが分かる。変数bのインデクス0のアドレスは0x0003であり、［６−４］のアドレス間参照関係データ１０１５から0x0003は0x0000と一致する。よって、図１９における行１３の参照アドレスは、0x0000となる。
【０１３４】
次にアドレス依存関係解析部１００５は、図１９のアドレス間定義−参照テーブル１００４に基づき、第一〜第四の実施例と同様の方法に従って、以下に示すアドレス依存テーブル１００７を作成する。
［６−５］
DD(7,0x0000,11)
DD(7,0x0000,12)
DD(7,0x0000,13)
DD(8,0x0002,11)
DD(10,0x0002,11)
【０１３５】
次に制御依存関係解析部１００６は、第一〜第四の実施例と同様の方法に従って、以下に示す制御依存テーブル１００８を作成する。
［６−６］
CD(11,12)
CD(11,13)
【０１３６】
次にスライス基準入力手段１００９からスライス基準（たとえば行番号）を入力する。
【０１３７】
たとえば［６−１］のターゲットプログラムにおいて、式１３（Ｌ１３）を選択した場合、式１３（Ｌ１３）に対するプログラム断片として、以下が抽出される。
L7: a[0] = 10;
L8: a[1] = 1;
L10: c = 0;
L11: if( a[c] > 10 ){
L13:   e = b[0];
}
【０１３８】
このようにして配列変数を持ち、配列変数のインデクスが変数で指定されたターゲットプログラムについても、プログラム断片を正しく抽出できる。
【図面の簡単な説明】
【０１３９】
【図１】第一の実施例に係るプログラム解析装置の機能ブロック図。
【図２】第一の実施例に係るプログラム解析装置の構成を示すハードウェアブロック図。
【図３】ターゲットプログラムの実行環境の一例を示す図。
【図４】第一の実施例に係る構文木の例を示す図。
【図５】第一の実施例に係る構文木の他の例を示す図。
【図６】第一の実施例に係るアドレス定義−参照関係解析部の動作フローを示すフローチャート。
【図７】第一の実施例に係るアドレス間定義―参照テーブルの一例を示す図。
【図８】第一の実施例に係るアドレス依存関係解析部の動作フローを示すフローチャート。
【図９】第一の実施例に基づく制御依存関係解析部の動作フローを示すフローチャート。
【図１０】第一の実施例に係るプログラム解析方法の一例を説明するフローチャート。
【図１１】第二の実施例に係る構文木の一例を示す図。
【図１２】第二の実施例に係るアドレス間定義−参照テーブルの一例を示す図。
【図１３】第三の実施例に係るプログラム解析装置の機能ブロック図。
【図１４】第三の実施例に係る構文木の一例を示す図。
【図１５】第三の実施例に係るアドレス間定義−参照テーブルの一例を示す図。
【図１６】第四の実施例に係るプログラム解析装置の機能ブロック図。
【図１７】第五の実施例に係るプログラム解析装置の機能ブロック図。
【図１８】第五の実施例に係る構文木の一例を示す図。
【図１９】第五の実施例に係るアドレス間定義−参照テーブルの一例を示す図。
【図２０】従来におけるプログラム解析装置の構成を示す図。
【図２１】従来技術に係る変数間定義−参照テーブルの一例を示す図。
【図２２】従来技術に係る変数間定義−参照テーブルの一例を示す図。
【図２３】従来技術に係る構文木の一例を示す図。
【符号の説明】
【０１４０】
１０００：ターゲットプログラム
１００１：変数−アドレス解析部
１００２：変数−アドレス対応テーブル
１００３：アドレス定義−参照関係解析部
１００４：アドレス間定義−参照テーブル
１００５：アドレス依存関係解析部
１００６：制御依存関係解析部
１００７：アドレス依存テーブル
１００８：制御依存テーブル
１００９：スライス基準入力手段
１０１０：スライス抽出部
１０１１：プログラム断片（部分プログラム、スライス）
１０１２：構文解析部
１０１３：構文木
１０１４：ポインタ解析部
１０１５：アドレス間参照関係データ
１０１６：変数−アドレス定義ファイル
１０１７：マップ構文解析部
１０１８：配列サイズ解析部
１１、２１：ＣＰＵ
１２：キーボード
１３：マウス
１４、２３：表示部
１５：メインメモリ
１６、２４：記憶装置
１７：バス
２２：ＲＡＭ
【図１】
2009237762.tif 000004
【図２】
2009237762.tif 000005
【図３】
2009237762.tif 000006
【図４】
2009237762.tif 000007
【図５】
2009237762.tif 000008
【図６】
2009237762.tif 000009
【図７】
2009237762.tif 000010
【図８】
2009237762.tif 000011
【図９】
2009237762.tif 000012
【図１０】
2009237762.tif 000013
【図１１】
2009237762.tif 000014
【図１２】
2009237762.tif 000015
【図１３】
2009237762.tif 000016
【図１４】
2009237762.tif 000017
【図１５】
2009237762.tif 000018
【図１６】
2009237762.tif 000019
【図１７】
2009237762.tif 000020
【図１８】
2009237762.tif 000021
【図１９】
2009237762.tif 000022
【図２０】
2009237762.tif 000023
【図２１】
2009237762.tif 000024
【図２２】
2009237762.tif 000025
【図２３】
2009237762.tif 000026