(57)【要約】      （修正有）【課題】複数の関数間で、関数の引数及びグローバル変数を利用することなく、変数を共有できるようにする。【解決手段】同一プロセス内の複数の関数の間で変数を共有する関数間変数共有機構１０を設ける。関数間変数共有機構は、値を格納して識別子によって値を参照することと値に代入することとができる識別子値記憶部２０と、複数の関数の間で共有される変数が参照されるときに、変数に対応する識別子を用いて識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡す識別子値参照部６０と、変数への代入のためにいずれかの関数から値を渡されたときに、変数に対応する識別子を用いて識別子値記憶部に格納されている値を変更する識別子値変更部４０と、を有する。【選択図】図４
2016186697.tif 000002
【特許請求の範囲】
【請求項１】
同一プロセス内の複数の関数の間で変数を共有する関数間変数共有方法であって、
値を格納して識別子によって前記値を参照することと前記値に代入することとができる識別子値記憶部を用い、前記複数の関数の間で共有される変数が参照されるときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡すことと、
いずれかの関数から値を渡されて前記変数に代入するときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を変更することと、
を有する方法。
【請求項２】
前記識別子値記憶部として環境変数の記憶領域を使用し、環境変数を定義して前記識別子として使用する、請求項１に記載の方法。
【請求項３】
前記識別子値記憶部としてプロセス間共有メモリを使用する、請求項１に記載の方法。
【請求項４】
前記識別子値記憶部として、前記プロセス間共有メモリ内に構築されたハッシュテーブルを使用し、該ハッシュテーブル内に前記識別子と前記値とを格納する、請求項３に記載の方法。
【請求項５】
前記同一プロセス内の複数の関数は、ヘッダーファイル内に記述された複数の関数を含む、請求項１乃至４のいずれか１項に記載の方法。
【請求項６】
前記同一プロセス内の複数の関数は、ヘッダーファイルのみで構成されるライブラリにおける複数のライブラリ関数を含む、請求項１乃至５のいずれか１項に記載の方法。
【請求項７】
同一プロセス内の複数の関数の間で変数を共有する関数間変数共有機構であって、
値を格納して識別子によって前記値を参照することと前記値に代入することとができる識別子値記憶部と、
前記複数の関数の間で共有される変数が参照されるときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡す識別子値参照部と、
前記変数への代入のためにいずれかの関数から値を渡されたときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を変更する識別子値変更部と、
を有する機構。
【請求項８】
前記識別子値記憶部として環境変数の記憶領域を使用し、
前記識別子値変更部は、前記関数から渡された前記識別子及び前記値を文字列に変換する第１の文字列変換部と、前記第１の文字列変換部によって変換された文字列を環境変数として前記記憶領域に設定する環境変数設定部と、を有し、
前記識別子値参照部は、前記記憶領域にアクセスして前記識別子に対応する環境変数を参照する環境変数参照部と、前記環境変数参照部によって参照された前記環境変数中に記録されている文字列を値の形式に変換する第２の文字列変換部と、を有する、請求項７に記載の機構。
【請求項９】
前記識別子値記憶部として、プロセス間共有メモリを使用し、
前記識別子値変更部は、前記プロセスのメモリ空間に前記プロセス間共有メモリを割り当てる第１の共有メモリ割り当て部と、前記プロセス間共有メモリ上のハッシュテーブルのアドレスを特定する第１のハッシュテーブル取得部と、前記特定されたアドレスを用いて前記ハッシュテーブル中の前記識別子に対応する値を変更するハッシュテーブル更新部と、を有し、
前記識別子値参照部は、前記プロセスのメモリ空間に前記プロセス間共有メモリを割り当てる第２の共有メモリ割り当て部と、前記プロセス間共有メモリ上の前記ハッシュテーブルのアドレスを特定する第２のハッシュテーブル取得部と、前記第２のハッシュテーブル取得部により特定された前記アドレスを用いて前記ハッシュテーブル中の前記識別子に対応する値を参照して前記関数に渡すハッシュテーブル参照部と、を有する、請求項７に記載の機構。
【請求項１０】
コンピュータにおいて同一プロセス内の複数の関数の間で変数を共有するためのプログラムであって、
前記コンピュータの記憶領域を、値を格納して識別子によって前記値を参照することと前記値に代入することとができる識別子値記憶部として使用させ、
前記コンピュータを、
前記複数の関数の間で共有される変数が参照されるときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡す識別子値参照手段、及び
前記変数への代入のためにいずれかの関数から値を渡されたときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を変更する識別子値変更手段、
として機能させるプログラム。
【発明の詳細な説明】
【技術分野】
【０００１】
本発明は、コンピュータプログラムの開発に関し、特に、同一プロセス内の異なる複数の関数の間で変数を共有するための方法及び機構に関する。
【背景技術】
【０００２】
Ｃ言語などによるプログラム開発では、ヘッダーファイルが利用される。一般にはヘッダーファイルには、変数や関数の宣言などが記述されている。ソースファイルの中でヘッダーファイルを読み込むべき位置に、ヘッダーファイルを指定してinclude文あるいはinclude（インクルード）指令（例えば、#include）を記載しておけば、指定されたヘッダーファイルがプリプロセッサによってソースファイル内に読み込まれる。複数のソースファイルで利用される関数の宣言をヘッダーファイルに記述しておけば、各ソースファイルそのそれぞれに関数の宣言を記述する必要がなく、ヘッダーファイルを読み込むだけでよい。また、ライブラリ関数の宣言が記述されたヘッダーファイルを利用すると、ライブラリ関数を利用するソースファイルに関数の宣言を記述する必要がなくなり、ライブラリの利便性が高まるという利点もある。
【０００３】
一方で、関数の定義自体をヘッダーファイルに記述することも行われる。コンパイラは一般に複数のソースファイルを個別にコンパイルするため、異なるソースファイルで定義された関数間に呼び出し関係があった場合にも、それらの関数間でインライン展開などの最適化を行わない。これに対してヘッダーファイルに関数の定義がある場合には、ヘッダーファイルはプリプロセッサによってソースファイルに読み込まれるため、コンパイラがソースファイルとヘッダーファイルで定義された関数との間での最適化を行うことができるという利点が生じる。このため、利用頻度が高い関数や、関数の大きさが小さい場合（すなわちインライン展開のデメリットが少ない場合）には、ヘッダーファイルにおいて関数定義を行うということがしばしば行われる。本明細書では、ヘッダーファイルで定義された関数を対象とする。
【０００４】
一般に、同一プロセス内の複数の関数間で変数の共有を行う場合は、関数の引数もしくはグローバル変数が用いられる。図１は、関数の引数によって、関数間で変数の共有を行う場合の例を擬似コードによって示している。この例では、関数func1及び関数func2の引数として、int（整数）型変数へのポインタを渡している。関数func1では、ポインタで示されたアドレスに値を書き込み、関数func2では、ポインタで示されたアドレスの値を参照している。このように複数の関数で同一の変数を利用することを、本明細書では変数の共有と呼ぶ。
【０００５】
引数を用いることで関数間での変数の共有が可能ではあるが、この場合、関数の呼び出し側に、引数を渡してもらう必要がある。共有する変数が、呼び出される関数のみで利用されるものである場合、呼び出し側にとって、本来、この変数は意識する必要のないものである。そのような変数を呼び出し側で管理することは、プログラムを複雑にするという課題を生ずる。なお、Ｃ＋＋のようなオブジェクト指向言語では、共有する変数にオブジェクトのメンバ変数を利用すると、オブジェクトのメンバ関数の引数として共有変数を渡す必要はなくなる。しかしながら、メンバ変数を利用する場合であっても、呼び出し側でオブジェクトを管理する必要があり、本質的には同じ課題が生ずる。すなわち、関数間で変数を共有するためだけにオブジェクトを利用することは、本来ならばオブジェクトを管理することは関数の呼び出し側には不要なことであるので、呼び出し側のプログラムを複雑にするという課題を生じる。
【０００６】
一方、図２は、グローバル変数を用いることによって関数間で変数の共有を行う場合の例を擬似コードによって示している。この例では、関数func1及び関数func2のほかに、グローバル変数flagが宣言されている。関数func1はグローバル変数に値の代入を行い、関数func2はグローバル変数の値を参照している。グローバル変数を用いることには、共有する変数を関数の引数によって渡すことなく、変数の共有が行えるという利点がある。しかしながらグローバル変数を用いる方法には、関数の定義とグローバル変数の定義とがヘッダーファイルに記述されている際に課題がある。このようなヘッダーファイルが同一プログラムを構成する複数のソースファイルから読み込まれる場合には、図３に示すように、グローバル変数が複数のソースファイルで定義されることになり、リンク時にエラーになるか、あるいは、本来ならば１つであるはずのグローバル変数がそれぞれ別々の変数として扱われて関数間で変数の共有ができなくなる。このような問題は、重複定義問題として知られている。グローバル変数の代わりにＣ＋＋のクラスの静的メンバ変数を用いる場合も、同様の課題が生じる。なお、特許文献１には、ネットワーク環境に対してグローバル変数による変数の共有を拡張したものとして、ネットワークに接続された複数のノード間でデータを共有するために、各データを論理名（ネットワークグローバル変数）で定義し、ユーザプログラムは論理名でそのデータを取得することが示されている。
【０００７】
この重複定義問題を回避する方法として、グローバル変数の定義をヘッダーファイルに記述するのではなく、ソースファイルに記述するという方法がある。グローバル変数の定義をソースファイルにおいて行う場合には、新たなソースファイルを追加するときや、既存のソースファイルにグローバル変数を追加するときなどに、プログラムの構成を複雑にしてしまうといった問題がある。さらにこの方法は、ヘッダーファイルだけから構成されいてオブジェクトファイルを持たないライブラリでは利用できない、といった問題もある。なお、オブジェクトファイルを持たないライブラリには、ヘッダーファイルをリンクするだけで利用できて使い勝手が良いという利点や、ライブラリ開発者がハードウェア固有のオブジェクトファイルを管理しないでよいといった利点があるため、ヘッダーファイルからだけなるライブラリからオブジェクトファイルをも有するライブラリへと変更することは、ライブラリの利用者とライブラリ開発者のどちらにとっても手間が増えるという問題をもたらす。
【０００８】
関数間で変数を共有することに関連し、特許文献２は、複数のコントローラ装置の各々ごとの制御プログラムを作成する際に共有データ定義の不整合の検査を行うために、各コントローラ装置に応じたプログラミング環境ごとに共有データ定義支援装置を設けることを開示している。各々の共有データ定義支援装置は、初期状態では同一内容である共有データ管理テーブルと、自装置の共有データ管理テーブルに基づいて生成される共有データ変数宣言テーブルとを備え、自装置及び他装置のこれらのテーブルに基づいて整合性検査を実行する。また特許文献３はソースファイルの再利用を支援する装置を開示しており、この装置では、アクティブソースファイル（編集対象となったソースファイル）から参照可能な定義データを、アクティブソースファイル内で定義されているローカル定義データとアクティブソース以外のソースファイル内で定義されている外部定義データとに区分して、各定義データに関する情報を取得、表示する。これによって利用者は、全ソースファイルで利用可能なグローバル変数も容易に検出可能となり、同一データを意味するグローバル変数の重複等を防ぐことができる。特許文献３に記載された技術は、利用者の介入によってグローバル変数の重複を防ごうとするものである。
【０００９】
さらに異なる複数のプロセス間でのデータ共有を行うものとして、特許文献４には、共有メモリ上に環境変数を配置するとともに、親子関係になくてもよい複数のプロセス間で環境変数を用いて変数を共有することが開示されている。なお、特許文献４に記載のものでは、異なるプロセス間で共有メモリを利用するため、異なるプロセスから共有メモリの場所を特定することを可能にするために、グローバル変数や引数に類する何らかの情報が必要になるものと考えられる。特許文献５には、ネットワークに接続された複数のコンピュータでネットワーク共有変数を共有する際に、型情報を有する共有変数を使用し、共有変数を読み出す関数は環境変数に対する参照（リファレンス）を引数として受け取ることを開示している。
【先行技術文献】
【特許文献】
【００１０】
【特許文献１】特開２００９−９６０７号公報
【特許文献２】特開２０１４−２３８８２０号公報
【特許文献３】特開２０１３−９７４７０号公報
【特許文献４】特開平７−１２９４１６号公報
【特許文献５】特開平１０−６３６２８号公報
【発明の概要】
【発明が解決しようとする課題】
【００１１】
複数の関数間で変数を共有する技術は知られているものの、それらは、引数あるいはグローバル変数を介するものであるので、上述したような課題を有する。グローバル変数や関数の引数を利用することなく同一プロセス内の異なる複数の関数の間で変数あるいはデータを共有する手法は知られていない。
【００１２】
本発明の目的は、同一プロセス内の異なる複数の関数間で、関数の引数及びグローバル変数を利用することなく、変数を共有するための方法及び機構を提供することにある。
【課題を解決するための手段】
【００１３】
本発明の例示態様によれば、関数間変数共有方法は、同一プロセス内の複数の関数の間で変数を共有する関数間変数共有方法であって、値を格納して識別子によって値を参照することと値に代入することとができる識別子値記憶部を用い、複数の関数の間で共有される変数が参照されるときに、変数に対応する識別子を用いて識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡すことと、いずれかの関数から値を渡されて変数に代入するときに、変数に対応する識別子を用いて識別子値記憶部に格納されている値を変更することと、を有する。
【００１４】
本発明の例示態様によれば、関数間変数共有機構は、同一プロセス内の複数の関数の間で変数を共有する関数間変数共有機構であって、値を格納して識別子によって値を参照することと値に代入することとができる識別子値記憶部と、複数の関数の間で共有される変数が参照されるときに、変数に対応する識別子を用いて識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡す識別子値参照部と、変数への代入のためにいずれかの関数から値を渡されたときに、変数に対応する識別子を用いて識別子値記憶部に格納されている値を変更する識別子値変更部と、を有する。
【発明の効果】
【００１５】
本発明によれば、同一プロセス内の複数の関数間で、関数の引数及びグローバル変数を利用することなく、変数を共有することができるようになる。
【図面の簡単な説明】
【００１６】
【図１】引数による関数間での変数の共有の例を説明する図である。
【図２】グローバル変数による関数間での変数の共有の例を説明する図である。
【図３】重複定義問題の例を説明する図である。
【図４】第１の実施形態の関数間変数共有機構の構成を示すブロック図である。
【図５】図４に示した関数間変数共有機構の動作を説明する図である。
【図６】第２の実施形態の関数間変数共有機構の構成を示すブロック図である。
【図７】第３の実施形態の関数間変数共有機構の構成を示すブロック図である。
【図８】（Ａ）〜（Ｃ）は、実施例で用いるファイルの内容を示す図である。
【図９】実施例でのヘッダーファイルtimer.hを示す図である。
【発明を実施するための形態】
【００１７】
次に、本発明の好ましい実施の形態について、図面を参照して説明する。
【００１８】
［第１の実施形態］
［構成］
図４は、第１の実施形態の関数間変数共有機構１０の構成を示している。図４に示す関数間変数共有機構１０は、同一プロセス内の異なる複数の関数の間で変数を共有するために用いられるものであり、値を格納して識別子によってその値を参照することとその値に代入することとができる識別子値記憶部２０と、識別子値記憶部２０に対してアクセス可能な識別子値変更部４０及び識別子値参照部６０と、を備えている。識別子値参照部６０は、同一プロセス内の複数の関数の間で共有される変数が参照されるときに、その変数に対応する識別子を呼び出し元の関数から受け取り、その識別子を用いて識別子値記憶部２０に格納されている値を読み出し、読み出した値を呼び出し元の関数に渡す機能を有する。一方、識別子値変更部４０は、変数への代入のために、呼び出し元の関数からその変数に対する識別子と代入すべきものとして指定された値を渡されたときに、渡された識別子を用いて識別子値記憶部２０に格納されている値を指定された値に変更する機能を有する。本実施形態において、識別子や値の具体的な形式としては、文字列や整数値などが利用可能であるが、特定の形式のものに限定されるものではない。
【００１９】
本実施形態において、関数間変数共有機構１０は、識別子と値のみが受け渡されるものであることを特徴とする。したがって、関数が関数間変数共有機構１０を利用することにより、識別子のみを用いて複数の関数の間で値を共有することが可能であり、グローバル変数や関数の引数を使うことなく、変数の共有が可能となる。
【００２０】
［動作］
次に、本実施形態の動作について詳しく説明する。本実施形態の動作は、大別すると、複数の関数の間で共有されることとなる変数の値の変更動作と、いずれかの関数からのその変数についての値の参照動作とからなる。
【００２１】
＜値の変更＞
値の変更では、まず、変数に対して値を代入する関数が、変数に対応する識別子と値の組み合わせを、識別子値変更部４０に渡す。次に識別子値変更部４０が、識別子値記憶部２０に記録されている識別子に対応する値を、関数から渡された値に変更する。
【００２２】
＜値の参照＞
値の参照では、まず、変数の値を参照しようとする関数が、変数に対応する識別子を、識別子値参照部６０に渡す。識別子が渡されことにより識別子値参照部６０は、識別子値記憶部２０に記録されている、識別子に対応する値を取得する。その後、識別子値参照部６０は、呼び出し元の関数に取得した値を渡す。
【００２３】
図５は、上述した第１の実施形態の効果を示している。図示される例では、関数１が識別子として文字列“flag”、値として整数値１を指定して、識別子値変更部４０を呼び出す。その結果、識別子値変更部４０が値の変更を行い、識別子値記憶部２０には識別子“flag”に対する値として１が記録される（図中の「<"flag", 1>」）。
【００２４】
次に関数２が識別子“flag”を指定して、識別子値参照部６０を呼び出す。識別子値参照部６０は、識別子値記憶部２０から、識別子“flag”に対応する値として、１を取り出し、関数２に返す。以上の動作により、関数１と関数２の間で値が受け渡される。
【００２５】
以上の関数間の値の受け渡しのために、識別子と値のみが関数内で利用されている。したがって本実施形態では、グローバル変数や関数の引数など利用せずに、関数間で変数を共有できるという効果が得られていることが分かる。また、これらの関数がヘッダーファイル内に記述されている場合においても、同様に変数を共有できるという効果が得られることは明らかである。本実施形態では、グローバル変数を利用していないため、ヘッダーファイルが複数のソースファイルに読み込まれる場合においても、関数間での変数の共有が可能であるという効果が得られる。
【００２６】
［第２の実施形態］
図６は、第２の実施形態の関数間変数共有機構１０の構成を示している。本実施形態は、環境変数を用いて複数の関数の間で変数を共有するものであり、したがって識別子値記憶部２０として、環境変数の記憶領域である環境変数記憶部２１を用いている。
【００２７】
環境変数は、複数のプロセス間で値を共有するためにＯＳ（オペレーティングシステム；operating system）などで提供される仕組みであり、Ｌｉｎｕｘ（登録商標）やＷｉｎｄｏｗｓ（登録商標）などのＯＳにおいて一般的に利用されている。環境変数は、プロセスの起動時に、プロセスのメモリ空間上の特定のアドレスに格納される文字列から構成される。文字列は、キーと値との１以上のペア（対）で構成され、これらを変数名及び値として利用することができる。ＯＳは、プロセスの起動時に、親プロセスの環境変数を子プロセスに引き継ぐように、子プロセスのメモリ空間を作成する。これにより、親プロセスで設定した環境変数を子プロセスが参照することができるようになる。このように環境変数は、一般に、親子プロセス間での変数の共有に利用される。
【００２８】
本実施形態では、このような環境変数の一般的な利用形態とは異なり、環境変数を同一プロセス内での関数間での変数の共有に利用するという特徴的な利用を行う。具体的には本実施形態は、環境変数はプロセスのメモリ空間中の固定アドレスに置かれるという性質を利用して、この固定アドレスに置かれた環境変数を用いて、同一プロセス内の関数間でデータを共有する。環境変数の設定と参照は識別子と値だけで行うことが可能であるため、本実施形態によれば、グローバル変数や関数の引数を利用しない、関数間変数共有のための仕組みを提供することができる。
【００２９】
図６に示すように本実施形態の関数間変数共有機構１０において、識別子値変更部４０は、関数から渡された識別子及び値を文字列に変換する文字列変換部４１と、文字列変換部４１によって変換された文字列を環境変数として、識別子値記憶部２０としての環境変数記憶部２１に設定する環境変数設定部４２と、を備えている。識別子値参照部６０は、環境変数記憶部２１にアクセスして識別子に対応する環境変数の値を参照する環境変数参照部６１と、環境変数参照部６１によって参照された環境変数中に記録されている文字列を値の形式に変換する文字列変換部６２と、を備えている。識別子が文字列でない場合には、環境変数参照部６１の前に、識別子を文字列に変換するさらになる文字列変換部を設け、この文字列変換部によって文字列に変換された識別子を環境変数参照部６１に渡すことが望ましい。
【００３０】
環境変数設定部４２と環境変数参照部６１の具体的な例としては、それぞれ、Ｌｉｎｕｘ（登録商標）におけるsetenv関数とgetenv関数がある。これらによる環境変数の設定、参照は一般によく知られているため、これらの詳細な動作の説明は省略する。第１の実施形態の説明とこれまでの説明から明らかであるため、本実施形態における動作及び効果についての説明を省略する。
【００３１】
［第３の実施の形態］
図７は、第３の実施形態の関数間変数共有機構１０の構成を示している。本実施形態は、識別子値記憶部２０として、プロセス間共有メモリ３１上のハッシュテーブル３２を利用することを特徴とするものである。プロセス間共有メモリは、複数のプロセス間でデータの受け渡し等を行うために共有メモリ空間を作成する機能であり、一般に、ＯＳによって提供されるものである。
【００３２】
プロセス間共有メモリは、key（キー）と呼ばれる一意な識別子（例えばＬｉｎｕｘ（登録商標）の場合は整数値）を有することができるが、keyを指定して特定のプロセス間共有メモリをプロセスのメモリ空間上にマップし、マップしたアドレスを知ることができる。すなわちkeyを知っていれば、プロセスのメモリ空間上の特定のメモリ領域のアドレスを特定できるということである。例えばkeyをプロセスＩＤにすれば、プロセスＩＤはプロセス中の任意の関数で取得することができるため、任意の関数がグローバル変数や関数の引数を使うことなく、特定のメモリ領域のアドレスを取得することができる。このメモリ領域にハッシュテーブルを作成し、関数間で共有したい変数の識別子と値とを格納することで、関数間で変数の共有を行うのが、本実施形態である。なお、本実施形態の説明では、識別子と値との記録にハッシュテーブル３２を利用しているが、識別子と値とを記録可能なその他のデータ構造を用いても良いことは明らかである。
【００３３】
図７に示すように本実施形態の関数間変数共有機構１０において、識別子値変更部４０は、共有メモリ割り当て部５１とハッシュテーブル取得部５２とハッシュテーブル更新部５３とを有する。
【００３４】
共有メモリ割り当て部５１は、特定のkey（例えばプロセスＩＤ）に対応するプロセス間共有メモリ３１をプロセスのメモリ空間に割り当てる機能を有し、プロセス間共有メモリ３１がまだ作成されていない場合はその作成を行う。共有メモリ割り当て部５１自体がプロセス間共有メモリ３１を作成するのではなく、keyに対応するプロセス間共有メモリ３１の作成をＯＳに対して指示する構成としてもよい。この場合、ＯＳは、プロセス間共有メモリ３１がまだ作成されていない場合にはそれを作成し、既に作成されている場合には何も行わない。
【００３５】
ハッシュテーブル取得部５２は、プロセス間共有メモリ３１上に作成されたハッシュテーブル３２のアドレスを特定する。例えば、プロセス間共有メモリ３１の領域の先頭にハッシュテーブル３２を配置するといった方法を取ることができる。また、ハッシュテーブル３２自体はヒープ領域に確保し、そのアドレスをプロセス間共有メモリ３１の先頭に格納するといった方法を用いても良い。また、ハッシュテーブル３２がまだ作成されていない場合は、ハッシュテーブル取得部５２は、プロセス間共有メモリ３１内にハッシュテーブル３２を新たに作成する。
【００３６】
ハッシュテーブル更新部５３は、ハッシュテーブル取得部５２によって特定されたアドレスを用いて、ハッシュテーブル３２中の識別子に対応する値を変更する機能を有する。なお、ハッシュテーブルに格納する識別子と値の形式が、関数から渡される識別子と値の形式と異なる場合には、適切に変換することが望ましい。このような変換を行うために、識別子値変更部４０に、識別子及び値をハッシュテーブル３２に適した形式に変換してハッシュテーブル更新部５３に渡す文字列変換部を備えてもよい。
【００３７】
一方、識別子値参照部６０は、共有メモリ割り当て部７１、ハッシュテーブル取得部７２及びハッシュテーブル参照部７３を備えている。共有メモリ割り当て部７１及びハッシュテーブル取得部７２は、それぞれ、識別子値変更部４０の共有メモリ割り当て部５１及びハッシュテーブル取得部５２と同一の機能を有する。ハッシュテーブル参照部７３は、ハッシュテーブル取得部７２により特定されたアドレスを用いて、ハッシュテーブル３２中の識別子に対応する値を参照し、呼び出し元の関数に渡す機能を有する。
【００３８】
本実施形態の関数間変数共有機構１０は、ハッシュテーブル３２が不要になったとき（例えばプロセスの終了時など）にプロセス間共有メモリ３１を解放する機能を有した共有メモリ解放部を備えていても良い。
【００３９】
第１及び第２の実施形態の説明とこれまでの説明から明らかであるため、本実施形態における動作及び効果についての説明を省略する。
【００４０】
以上説明した各実施形態によれば、ヘッダーファイルのみで構成されたライブラリにおいても複数の関数間で変数を共有できるようになる。したがって、利用者の利便性が高いライブラリを提供することや、開発者の負担が少ないライブラリを提供するといったことが可能となる。
【００４１】
上述した各実施形態の関数間変数共有機構１０において、識別子値記憶部２０としては、異なる複数の関数を含むプロセスが実行されるコンピュータの記憶装置内の所定の領域を用いることができる。識別子値変更部４０及び識別子値参照部６０は、それぞれ専用のハードウェアによって構成することも可能ではあるが、関数間で変数を共有するためのプログラムを前述したプロセスを実行するコンピュータ上で実行させることによって実現することができる。このように関数間変数共有機構１０をコンピュータソフトウェアで実現する場合には、そのためのプログラムをコンピュータに読み込ませてコンピュータに実行させればよい。このプログラムは、通信インタフェースなどを介して外部装置から読み込まれ、あるいは、コンピュータ読み取り可能な記憶媒体から読み込まれ、予め、記憶装置格納される。さらには、上述した関数間変数共有機構１０の機能は、コンピュータのＯＳにおいて予め実装することもできる。
【実施例】
【００４２】
次に、具体的な実施例を用いて上述した実施形態の動作を説明する。ここで説明例は、プログラム中の任意の区間の時間を計測するタイマライブラリをヘッダーファイルのみで構成する場合の例である。
【００４３】
ここでは、ライブラリは以下の３つの関数から構成されるものとし。いずれもtimer.h内で定義されているものとする。
【００４４】
timer＿begin(int id)  時間計測の開始
timer＿end(int id)    時間計測の終了
timer＿output()       測定結果の出力
これらの関数は、図９に示すように利用される。この例では、プログラムはそれぞれＣ言語で記載された関数を示すmain.c、func1.c及びfunc2.cの３つのファイルからなっており、それぞれがtimer.hをインクルードしている。timer.hは、ヘッダーファイルのみで構成されたタイマライブラリである。これらのプログラムでは、関数func1及び関数func2内の特定の区間の時間を計測するため、上記の時間計測関数がそれぞれの関数内に挿入されている。また、計測結果を出力するため、main関数の最後に結果出力関数timer＿output()が呼び出されており、func1とfunc2の実行時間の計測を行って、その結果を出力するようになっている。
【００４５】
一般に、時間計測を行う際は、計測した値を記録し、それをプログラムの最後で出力するという利用方法が取られる。計測を行うたびに出力を行うと、出力に要する処理時間がプログラムの実行時間に影響を与えて、正しく時間計測が行えないことなどの問題があるためである。したがって、計測した値を記録しておく領域が必要となり、時間計測関数（本例ではtimer＿begin関数やtimer＿end関数）や出力関数（本例ではtimer＿output関数）は、その領域を特定できる必要がある。すなわち、これらの関数間で領域を共有する必要がある。
【００４６】
一方で、時間計測ライブラリの利用者にとっては時間の計測が目的であり、測定結果を記録するための領域には関心がない。したがって、ライブラリ利用者がそのような領域の管理を行う必要がないことが望ましい。本実施例の時間計測ライブラリは、上記のように計測区間を指定するＩＤのみを引数としてとり、ライブラリ利用者が計測結果記録用の領域を扱う必要がない利便性の高いライブラリとなっている。
【００４７】
図９は、この実施例での時間計測ライブラリtimer.hを示している。ここでは環境変数を用いて関数間での変数の共有を行うものとする。したがって、識別子値記憶部２０としては、環境変数の記憶領域すなわち環境変数記憶部２１が用いられる。時間計測ライブラリtimer.hのソースコードのうち、get関数が識別子値参照部６０の機能を実行し、set関数が識別子値変更部４０の機能を実行する。図９に示すように、get関数は、識別子として文字列nameを引数として受け取り、getenv関数を呼び出して、環境変数nameの値を取得する。getenv関数はＬｉｎｕｘ（登録商標）などが備えている一般的なものであるから説明を省略する。getenv関数によりnameに対応する文字列が得られるため、get関数はその後、取得した値をポインタ値に変換して返却する。文字列からポインタ値への変更方法は周知のものであるので、ここでは説明を省略する。環境変数が設定されていない場合は、get関数はNULL（ヌル）を返却する。一方、set関数は、識別子として文字列name、値としてポインタ値ptrを受け取る。set関数は、ptrを文字列に変換し、setenv関数を呼び出すことによって、環境変数に値を格納する。この実施例のget関数及びset関数は、渡されたnameをそのまま環境変数として利用しているが、プレフィックスをつけるなどにより、既存の環境変数との重複を避けるようにしてもよい。
【００４８】
次にこの実施例の時間計測関数について説明する。timer＿begin関数は、まず時刻を計測し、それを記録するという動作を行う。get＿clock関数の呼び出し部分が時刻の計測であるが、これは、一般的なＯＳは備えられている関数であるので、その詳細についての説明は省略する。計測後、get関数を呼び出して、計測結果を格納するためのテーブルのアドレスを取得する。もしテーブルがまだ作成されていない場合（NULLの場合）、新たにテーブルを作成して、set関数を呼び出して、テーブルのアドレスを格納する。最後にテーブルに測定値を書き込む。timer＿end関数は、同様にまず時間計測を行う。その後、get関数を呼び出して、結果格納用のテーブルを取得し、テーブルに値を格納する。timer＿output関数は、結果格納用のテーブルをget関数によって取得し、結果出力を行う。このようにget関数及びset関数を用いることによって、この実施例では、timer＿begin関数、timer＿end関数及びtimer＿output関数の各関数間で、グローバル変数や引数を用いることなく、結果格納用テーブルの共有を行うことができている。
【００４９】
ところでこの実施例では、図８に示したように、timer.hは複数のファイル（すなわち、main.c、func1.c及びfunc2.c）でインクルードされているため、timer.hにおいてグローバル変数を利用した場合は、重複定義の問題が起こることは明らかである。このように、本発明に基づく方法を用いることによって、この実施例では、ライブラリの利用者にとっての利便性が高い時間計測ライブラリを提供できるといった効果がある。また、ライブラリの開発者にとっては、オブジェクトファイルを管理しなくて良いといった効果もある。
【００５０】
上記の実施形態及び実施例の一部または全部は、以下の付記のようにも記載されうるが、以下には限られない。
【００５１】
［付記１］
同一プロセス内の複数の関数の間で変数を共有する関数間変数共有方法であって、
値を格納して識別子によって前記値を参照することと前記値に代入することとができる識別子値記憶部を用い、前記複数の関数の間で共有される変数が参照されるときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡すことと、
いずれかの関数から値を渡されて前記変数に代入するときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を変更することと、
を有する方法。
【００５２】
［付記２］
前記識別子値記憶部として環境変数の記憶領域を使用し、環境変数を定義して前記識別子として使用する、付記１に記載の方法。
【００５３】
［付記３］
前記識別子値記憶部としてプロセス間共有メモリを使用する、付記１に記載の方法。
【００５４】
［付記４］
前記識別子値記憶部として、前記プロセス間共有メモリ内に構築されたハッシュテーブルを使用し、該ハッシュテーブル内に前記識別子と前記値とを格納する、付記３に記載の方法。
【００５５】
［付記５］
前記識別子値記憶部に、前記識別子と前記値とを組にして格納する、付記１に記載の方法。
【００５６】
［付記６］
前記同一プロセス内の複数の関数は、ヘッダーファイル内に記述された複数の関数を含む、付記１乃至５のいずれか１項に記載の方法。
【００５７】
［付記７］
前記同一プロセス内の複数の関数は、ヘッダーファイルのみで構成されるライブラリにおける複数のライブラリ関数を含む、付記１乃至６のいずれか１項に記載の方法。
【００５８】
［付記８］
同一プロセス内の複数の関数の間で変数を共有する関数間変数共有機構であって、
値を格納して識別子によって前記値を参照することと前記値に代入することとができる識別子値記憶部と、
前記複数の関数の間で共有される変数が参照されるときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡す識別子値参照部と、
前記変数への代入のためにいずれかの関数から値を渡されたときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を変更する識別子値変更部と、
を有する機構。
【００５９】
［付記９］
前記識別子値記憶部として環境変数の記憶領域を使用し、
前記識別子値変更部は、前記関数から渡された前記識別子及び前記値を文字列に変換する第１の文字列変換部と、前記第１の文字列変換部によって変換された文字列を環境変数として前記記憶領域に設定する環境変数設定部と、を有し、
前記識別子値参照部は、前記記憶領域にアクセスして前記識別子に対応する環境変数を参照する環境変数参照部と、前記環境変数参照部によって参照された前記環境変数中に記録されている文字列を値の形式に変換する第２の文字列変換部と、を有する、付記８に記載の機構。
【００６０】
［付記１０］
前記識別子値参照部は、前記識別子を文字列に変換して前記環境変数参照部に渡す第３の文字列変換部を有する、付記９に記載の機構。
【００６１】
［付記１１］
前記識別子値記憶部として、プロセス間共有メモリを使用する、付記８に記載の機構。
【００６２】
［付記１２］
前記識別子値記憶部として、プロセス間共有メモリを使用し、
前記識別子値変更部は、前記プロセスのメモリ空間に前記プロセス間共有メモリを割り当てる第１の共有メモリ割り当て部と、前記プロセス間共有メモリ上のハッシュテーブルのアドレスを特定する第１のハッシュテーブル取得部と、前記特定されたアドレスを用いて前記ハッシュテーブル中の前記識別子に対応する値を変更するハッシュテーブル更新部と、を有し、
前記識別子値参照部は、前記プロセスのメモリ空間に前記プロセス間共有メモリを割り当てる第２の共有メモリ割り当て部と、前記プロセス間共有メモリ上の前記ハッシュテーブルのアドレスを特定する第２のハッシュテーブル取得部と、前記第２のハッシュテーブル取得部により特定された前記アドレスを用いて前記ハッシュテーブル中の前記識別子に対応する値を参照して前記関数に渡すハッシュテーブル参照部と、を有する、付記８に記載の機構。
【００６３】
［付記１３］
前記識別子値変更部は、前記識別子及び値を前記ハッシュテーブルに適した形式に変換して前記ハッシュテーブル更新部に渡す文字列変換部を有する、付記１２に記載の機構。
【００６４】
［付記１４］
前記識別子値記憶部に、前記識別子と前記値とを組にして格納する、付記８に記載の機構。
【００６５】
［付記１５］
前記同一プロセス内の複数の関数は、ヘッダーファイル内に記述された複数の関数を含む、付記８乃至１４のいずれか１項に記載の機構。
【００６６】
［付記１６］
前記同一プロセス内の複数の関数は、ヘッダーファイルのみで構成されるライブラリにおける複数のライブラリ関数を含む、付記８乃至１５のいずれか１項に記載の機構。
【００６７】
［付記１７］
コンピュータにおいて同一プロセス内の複数の関数の間で変数を共有するためのプログラムであって、
前記コンピュータの記憶領域を、値を格納して識別子によって前記値を参照することと前記値に代入することとができる識別子値記憶部として使用させ、
前記コンピュータを、
前記複数の関数の間で共有される変数が参照されるときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を読み出して呼び出し元の関数に渡す識別子値参照手段、及び
前記変数への代入のためにいずれかの関数から値を渡されたときに、前記変数に対応する識別子を用いて前記識別子値記憶部に格納されている値を変更する識別子値変更手段、
として機能させるプログラム。
【符号の説明】
【００６８】
１０    関数間変数共有機構
２０    識別子値記憶部
２１    環境変数記憶部
３１    プロセス間共有メモリ
３２    ハッシュテーブル
４０    識別子値変更部
４１，６２    文字列変換部
４２    環境変数設定部
５１，７１    共有メモリ割り当て部
５２，７２    ハッシュテーブル取得部
５３    ハッシュテーブル更新部
６０    識別子値参照部
６１    環境変数参照部
７３    ハッシュテーブル参照部
【図１】
2016186697.tif 000003
【図２】
2016186697.tif 000004
【図３】
2016186697.tif 000005
【図４】
2016186697.tif 000006
【図５】
2016186697.tif 000007
【図６】
2016186697.tif 000008
【図７】
2016186697.tif 000009
【図８】
2016186697.tif 000010
【図９】
2016186697.tif 000011