JP1/Script(Windows(R)用)

[目次][用語][索引][前へ][次へ]

9.6.1 CallDllDLLファイルを呼び出す

機能
DLLファイルを呼び出します。
形式
CallDll ( DllFileName , FunctionName , Param1 , Param2 , … )
指定項目
DllFileName
DLLファイル名を,文字列,または値を格納した変数名で指定します。
FunctionName
呼び出す外部関数名を,文字列,または値を格納した変数名で指定します。
Param132
関数のパラメタを,文字列,または値を格納した変数名で指定します。
複数のパラメタを指定できます。
JP1/Script 06-00以降では,複数のパラメタを一つずつ格納した配列変数を変数名で指定することもできます。
説明
指定されたDLLをロードし,外部関数をコールします。コマンドが正常に実行された場合は真(True)を,エラーが発生した場合は偽(False)を,コマンドの実行結果として返します。
外部関数は次のインタフェースにしてください。また,モジュール定義ファイル(.DEF)のEXPORTSセクションに外部参照宣言が必要になります。
宣言
BOOL  WINAPI  MyFunc( HWND hParent, int argc, char * argv[], int * rtnc, char * * rtnv[] );
引数
HWND  hParent;   ' 親ウィンドウのハンドル
int  argc;   ' スクリプトから渡されるパラメタの数
char *  argv[];   ' スクリプトから渡されるパラメタの配列
int *  rtnc;   ' スクリプトに返す文字列の数を格納するポインタ
char * * rtnv[];   ' スクリプトに返す文字列の配列を格納するポインタ
戻り値
外部関数MyFuncの戻り値は_DLL_RTN_予約変数に格納します。_DLL_RTN_予約変数がTrueの場合,引数rtnvに格納されたスクリプトに返す文字列の配列はスクリプト上で_RTNxx_予約変数を使って参照できます。 xxは00から順に引数rtncに格納された数だけ割り振られます。外部関数MyFuncの戻り値がFalseの場合,_RTNxx_予約変数は定義されません。
スクリプトに返す文字列,および文字列配列は,関数終了後も参照できるように,関数のスコープ内のローカルバッファには格納しないでください。
補足
ロードしたDLLファイルは,コマンドの実行終了時にアンロードされます。ロードしたDLLファイルをアンロードしたくない場合は,次に示すレジストリの値に「1」を設定してください。一度ロードしたDLLファイルは,スクリプトの実行が終了するまでアンロードされません。
〔レジストリキー〕
HKEY_LOCAL_MACHINE\SOFTWARE\HITACHI\JP1/Script\SPTX
〔値名〕
CallDllUnloadMode
〔値のデータタイプ〕
REG_DWORD
〔値〕
0:DLLファイルをアンロードする
1:DLLファイルをアンロードしない
〔設定が有効になるタイミング〕
スクリプトファイルの次回実行時
注意
DLLファイルをアンロードしない設定にした場合の注意事項を次に示します。
  • DLLのエントリポイント関数であるDllMain関数は,DLLファイルをロードするときにWindowsシステムから呼び出されて実行されます。したがって,同じDLLファイルを指定したCallDllコマンドを複数回実行する場合は,最初に実行するときはDLLファイルをロードするためDllMain関数が実行されますが,2回目以降の実行のときはDLLファイルをロードしないため,DllMain関数は実行されません。
  • DLLの中で使用する外部変数は,DLLファイルをロードするときに初期化されます。したがって,同じDLLファイルを指定したCallDllコマンドを複数回実行する場合は,最初に実行するときはDLLファイルをロードするため外部変数が初期化されますが,2回目以降の実行のときはDLLファイルをロードしないため,外部変数が初期化されません。
  • 実体が異なる同一名称のDLLファイルを指定する場合は,絶対パスで指定してください。実体が異なる同一名称のDLLファイルを相対パスで指定している場合,SetPathコマンドで実行フォルダのパスを設定してもWindowsシステムは同じDLLファイルと認識するため,DLLファイルはロードされません。
  • CallDllコマンドでコールする外部関数を一つにまとめたDLLファイルをできるだけ使用してください。複数の異なるDLLファイルを指定したCallDllコマンドを多用すると,スクリプトの実行プロセス中に多数のDLLファイルをロードすることになるため,メモリ不足が発生するおそれがあります。
' TEST.DLLの関数部分(Favorite.c)
#include "windows.h"
 
#define  FAV_SPORT1 "SKI"
#define  FAV_SPORT2 "BASKETBALL"
#define  FAV_FOOD1  "STEAK"
#define  FAV_FOOD2  "PASTA"
char *  g_ret[2];
 
BOOL  WINAPI  GetFavorite( HWND hParent, int argc, char * argv[], int * rtnc, char ** rtnv[] )
{
  if (lstrcmp(argv[0], "SPORT") == 0)
  {
    g_ret[0] = FAV_SPORT1;
    g_ret[1] = FAV_SPORT2;
  }
  else if (lstrcmp(argv[0], "FOOD") == 0)
  {
    g_ret[0] = FAV_FOOD1 ;
    g_ret[1] = FAV_FOOD2;
  }
 
  *rtnc = 2;
  *rtnv = g_ret;
 
  return ( TRUE );
}
 
' スクリプト側の処理(abc.SPT)
Dim  Quest
Quest = "SPORT"
CallDll(_BIN_+"TEST.DLL" ,"GetFavorite" ,Quest)
Dim  Msg
Msg = "私の好きな"+Quest+"は"+_RTN00_+"と"+_RTN01_+"です"
MessageBox(Msg ,OK,,Information)
Exit(0)
対象バージョン
JP1/Script 01-00以降