Javaのプログラムを呼び出す
Javaのプログラムを呼び出す方法としては、コンソールからjava.exeを使って実行する方法が殆どで、例えばネットワークインターフェースの情報を取得するプログラムで利用したIfInfoTest.javaだと
java -cp c:\java\net\classes net.test.IfInfoTest
として起動するとか、コマンドライン実行が面倒な場合には、上記コマンドをfoo.batのようにバッチファイル化して起動する方法などが考えられます。
ただ個人的には、コマンドラインで呼び出したりバッチファイルにするのはスマートでなかったり、アイコンを定義できなかったりと不便なのと、それにJavaアプリケーションをWindowsサービスとして登録したかったこともあったので、C++のプログラムから呼び出すクラスを作ってみました。
JvmEnvクラスでは、JNIを起動する時に必要な環境の構築と情報の保持を行います。
JvmEnv.h
#ifndef _JVM_ENV_CLASS #define _JVM_ENV_CLASS #include <windows.h> #include <tchar.h> #include <comdef.h> #include <string> #include <vector> #include <map> typedef std::basic_string<_TCHAR> String; typedef std::vector<String> string_array; typedef std::map<String, String> string_map; typedef std::pair<String, String> string_pair; typedef string_map::iterator psmap; typedef std::map<String, void *> pointer_map; typedef std::pair<String, void *> pointer_pair; typedef pointer_map::iterator ppmap; #include <jni.h> typedef jint (WINAPI *lpJNI_GetDefaultJavaVMInitArgs)(void *args); typedef jint (WINAPI *lpJNI_CreateJavaVM)(JavaVM **pvm, void **penv, void *args); typedef jint (WINAPI *lpJNI_GetCreatedJavaVMs)(JavaVM **, jsize, jsize *); typedef void (WINAPI *lpPrintRoutine)(FILE *file, const char *format, va_list args); typedef void (WINAPI *lpAbortRoutine)(); typedef void (WINAPI *lpExitRoutine)(int code); // Java environment access type extern const int JDKJavaHome; extern const int JDKRuntimeLib; extern const int JREJavaHome; extern const int JRERuntimeLib; extern const int CurrentVersion; extern const int TargetVersion; extern const int LatestVersion; class JvmEnv { private: void copy(const JvmEnv& from); static String getRegValue(HKEY hkey, String valueKey, DWORD type); static void JNICALL jni_vfprintf(FILE *file, const char *format, va_list args); static void JNICALL jni_exit(jint code); static void JNICALL jni_abort(); public: JvmEnv(); JvmEnv(const JvmEnv& from); ~JvmEnv(); JvmEnv& operator=(const JvmEnv& original); void loadArgs(int argc, _TCHAR* argv[], bool first_program = true); void addProgParam(String argv); void addJavaParam(String argv); void setJLibName(String libpath); int loadJLib(String libpath = String()); int unloadJLib(); int createJvm(); JavaVM *getJvm(); jobjectArray jvmArgs(JNIEnv* jEnv); int destroyJvm(); String getCallerName(); void addClassPath(String path, String file = String()); String getClassPath(); static void setPrintRoutine(lpPrintRoutine routine); static void setAbortRoutine(lpAbortRoutine routine); static void setExitRoutine(lpExitRoutine routine); static string_map installedJvm(int type); static String findJvm(int type, bool version = true, String basic = String()); private: string_array prog_params; string_array java_params; string_array class_path; String vm_lib; String caller_name; JavaVM *jvm; JNIEnv *jni_env; HINSTANCE hjvm; lpJNI_GetDefaultJavaVMInitArgs fnJNI_GetDefaultJavaVMInitArgs; lpJNI_CreateJavaVM fnJNI_CreateJavaVM; lpJNI_GetCreatedJavaVMs fnJNI_GetCreatedJavaVMs; }; // class JvmEnv #endif // _JVM_ENV_CLASS
JvmEnv.cpp
#include "jvmenv.h" #include "jvmservice.h" const int JavaHome = 0x01; const int RuntimeLib = 0x02; const int JDK_BASE = 0x04; const int JDK = JDK_BASE; const int JDKJavaHome = (JDK_BASE+JavaHome); const int JDKRuntimeLib = (JDK_BASE+RuntimeLib); const int JRE_BASE = 0x08; const int JRE = JRE_BASE; const int JREJavaHome = (JRE_BASE+JavaHome); const int JRERuntimeLib = (JRE_BASE+RuntimeLib); const int CurrentVersion = 0x80; const int TargetVersion = CurrentVersion+0x10; const int LatestVersion = CurrentVersion+0x20; const String JAVA_ROOT = String(_T("SOFTWARE\\JavaSoft")); const String JDK_PATH = String(_T("\\Java Development Kit")); const String JRE_PATH = String(_T("\\Java Runtime Environment")); const String CURRENT_VERSION = String(_T("CurrentVersion")); const char *szJNI_GetDefaultJavaVMInitArgs = "JNI_GetDefaultJavaVMInitArgs"; const char *szJNI_CreateJavaVM = "JNI_CreateJavaVM"; const char *szJNI_GetCreatedJavaVMs = "JNI_GetCreatedJavaVMs"; #define BUFF_SIZE 256 static lpPrintRoutine print_routine = NULL; static lpAbortRoutine abort_routine = NULL; static lpExitRoutine exit_routine = NULL; /* * JvmEnvの値をコピーする * param : コピー元のデータ(JvmEnvクラス) * * return : 無し */ void JvmEnv::copy(const JvmEnv& from) { for (size_t i = 0; i < from.prog_params.size(); i++) prog_params.push_back(from.prog_params.at(i)); for (size_t i = 0; i < from.java_params.size(); i++) java_params.push_back(from.java_params.at(i)); for (size_t i = 0; i < from.class_path.size(); i++) class_path.push_back(from.class_path.at(i)); vm_lib = from.vm_lib; caller_name = from.caller_name; jvm = from.jvm; jni_env = from.jni_env; hjvm = from.hjvm; fnJNI_GetDefaultJavaVMInitArgs = from.fnJNI_GetDefaultJavaVMInitArgs; fnJNI_CreateJavaVM = from.fnJNI_CreateJavaVM; fnJNI_GetCreatedJavaVMs = from.fnJNI_GetCreatedJavaVMs; } /* * Registoryからデータを取得する * param : Registoryキー(HKEY) * データキー(String) * データタイプ(DWORD) * * return : String */ String JvmEnv::getRegValue(HKEY hkey, String valueKey, DWORD type) { DWORD buffSize = 0; DWORD valueType = type; int rc; rc = RegQueryValueEx(hkey, valueKey.c_str(), 0, &valueType, NULL, &buffSize); String result; if (rc == ERROR_SUCCESS) { buffSize++; char *buff = (char *)calloc(buffSize, sizeof(char)); if (buff != NULL) { if (RegQueryValueEx(hkey, valueKey.c_str(), 0, &valueType, (LPBYTE)buff, &buffSize) == ERROR_SUCCESS) { result = String((_TCHAR*)buff); } free(buff); } } return result; } /* * print_routineの呼出 * param : 出力ファイル(FILEポインター) * フォーマット(const charポインター) * パラメータリスト(va_list) * * return : 無し */ void (JNICALL JvmEnv::jni_vfprintf)(FILE *file, const char *format, va_list args) { if (print_routine != NULL) print_routine(file, format, args); } /* * abort_routineの呼出 * param : 無し * * return : 無し */ void (JNICALL JvmEnv::jni_abort)() { if (abort_routine != NULL) abort_routine(); } /* * exit_routineの呼出 * param : exitコード(int) * * return : 無し */ void (JNICALL JvmEnv::jni_exit)(jint code) { if (exit_routine != NULL) exit_routine(code); } // Constructer JvmEnv::JvmEnv() { jvm = NULL; jni_env = NULL; hjvm = NULL; fnJNI_GetDefaultJavaVMInitArgs = NULL; fnJNI_CreateJavaVM = NULL; fnJNI_GetCreatedJavaVMs = NULL; } // Copy Constructer JvmEnv::JvmEnv(const JvmEnv& from) { copy(from); } // Destructer JvmEnv::~JvmEnv() { } /* * "=(代入)"オペレータの処理 */ JvmEnv& JvmEnv::operator=(const JvmEnv& original) { copy(original); return *this; } /* * プログラム起動時のパラメータを保存する * param : パラメータの数(int) * パラメータ(_TCHARポインター) * * return : 無し */ void JvmEnv::loadArgs(int argc, _TCHAR* argv[], bool first_program) { for (int i = 0; i < argc; i++) { if (first_program && (i == 0)) caller_name = String(argv[i]); else { if ((argv[i][0] == _T('-')) && (argv[i][1] != _T('-'))) { java_params.push_back(String(argv[i])); } else { prog_params.push_back(String(argv[i])); } } } } /* * プログラム実行用パラメータを追加する * param : パラメータ(String) * * return : 無し */ void JvmEnv::addProgParam(String argv) { prog_params.push_back(argv); } /* * Javaの起動用パラメータを追加する * param : パラメータ(String) * * return : 無し */ void JvmEnv::addJavaParam(String argv) { java_params.push_back(argv); } /* * JavaVM Libraryの名前を指定する * param : JavaVM Libraryの名前(String) * * return : 無し */ void JvmEnv::setJLibName(String libpath) { vm_lib = libpath; } /* * JavaVM Libraryをロードし、ファンクションのアドレスを取得する * param : JavaVM Libraryの名前(String) * * return : int */ int JvmEnv::loadJLib(String libpath) { if (!libpath.empty()) { vm_lib = libpath; } else { if (vm_lib.empty()) { vm_lib = findJvm(JRERuntimeLib+LatestVersion, false); } } if (!vm_lib.empty()) { hjvm = LoadLibrary(vm_lib.c_str()); if (hjvm != NULL) { fnJNI_GetDefaultJavaVMInitArgs = (lpJNI_GetDefaultJavaVMInitArgs)GetProcAddress(hjvm, szJNI_GetDefaultJavaVMInitArgs); if (fnJNI_GetDefaultJavaVMInitArgs == NULL) { return -1; } fnJNI_CreateJavaVM = (lpJNI_CreateJavaVM)GetProcAddress(hjvm, szJNI_CreateJavaVM); if (fnJNI_CreateJavaVM == NULL) { return -2; } fnJNI_GetCreatedJavaVMs = (lpJNI_GetCreatedJavaVMs)GetProcAddress(hjvm, szJNI_GetCreatedJavaVMs); if (fnJNI_GetCreatedJavaVMs == NULL) { return -4; } } else { return -64; } } else { return -128; } return 0; } /* * JavaVM Libraryをアンロードする * param : 無し * * return : int */ int JvmEnv::unloadJLib() { if (hjvm != NULL) { if (FreeLibrary(hjvm)) { return -128; } fnJNI_GetDefaultJavaVMInitArgs = NULL; fnJNI_CreateJavaVM = NULL; fnJNI_GetCreatedJavaVMs = NULL; } hjvm = NULL; return 0; } /* * JavaVMを初期化する * param : 無し * * return : int */ int JvmEnv::createJvm() { JavaVMInitArgs vm_args; vm_args.version = JNI_VERSION_1_6; fnJNI_GetDefaultJavaVMInitArgs(&vm_args); size_t array_len = (java_params.size() + 4) * sizeof(JavaVMOption); JavaVMOption *option_array = (JavaVMOption *)malloc(array_len); memset(option_array, 0, array_len); size_t pos = 0; for (pos = 0; pos < java_params.size(); pos++) { option_array[pos].optionString = _strdup((char *)_bstr_t(java_params.at(pos).c_str())); } option_array[pos++].optionString = _strdup((char *)_bstr_t(getClassPath().c_str())); option_array[pos].optionString = "vfprintf"; option_array[pos++].extraInfo = (void *)jni_vfprintf; option_array[pos].optionString = "abort"; option_array[pos++].extraInfo = (void *)jni_abort; option_array[pos].optionString = "exit"; option_array[pos++].extraInfo = (void *)jni_exit; vm_args.version = JNI_VERSION_1_6; vm_args.options = option_array; vm_args.nOptions = (jint)(java_params.size() + 4); vm_args.ignoreUnrecognized = JNI_TRUE; int rc = fnJNI_CreateJavaVM(&jvm, (void**)&jni_env, &vm_args); for (size_t i = 0; i < java_params.size()+1; i++) { free(option_array[i].optionString); } free(option_array); if (rc != JNI_OK) return -128; return 0; } /* * JavaVMを終了する * param : 無し * * return : int */ int JvmEnv::destroyJvm() { if (jvm != NULL) { if (jvm->DestroyJavaVM() != JNI_OK) { return -128; } } jvm = NULL; return 0; } /* * JavaVMを取得する * param : 無し * * return : JavaVMポインター */ JavaVM *JvmEnv::getJvm() { return jvm; } /* * JavaVM用パラメータを取得する * param : 無し * * return : jobjectArray */ jobjectArray JvmEnv::jvmArgs(JNIEnv* jni_env) { jclass clazz = jni_env->FindClass("java/lang/String"); if (clazz == NULL) { return NULL; } size_t num = prog_params.size(); jobjectArray ja = jni_env->NewObjectArray((jsize)num, clazz, NULL); for(size_t i = 0; i < num; i++) { String c_string = prog_params.at(i); _bstr_t value = _bstr_t((_TCHAR *)c_string.c_str()); jstring j_string = jni_env->NewString((const jchar *)((wchar_t *)value), (jsize)value.length()); jni_env->SetObjectArrayElement(ja, (jsize)i, j_string); } return ja; } /* * 実行プログラム名を取得する * param : 無し * * return : String */ String JvmEnv::getCallerName() { return caller_name; } /* * クラスパスを追加する * param : クラスパス(String) * * return : void */ void JvmEnv::addClassPath(String path, String file) { if (file.empty()) class_path.push_back(path); else { String full_path = path; full_path.append(_T("\\")); full_path.append(file); class_path.push_back(full_path); } } /* * クラスパスを取得する * param : 無し * * return : String */ String JvmEnv::getClassPath() { String path; if (!class_path.empty()) { path = String(_T("-Djava.class.path=")); for (size_t i = 0; i < class_path.size(); i++) { if (i > 0) path.append(_T(";")); path.append(class_path.at(i)); } } return path; } /* * 導入済みのJava情報を取得する * param : 確認するJavaのタイプ(int) * * return : string_map */ string_map JvmEnv::installedJvm(int type) { string_map result; string_array vers; unsigned long buffSize = BUFF_SIZE; HKEY hkey = NULL; HKEY hVKey = NULL; FILETIME ft; String subkey = JAVA_ROOT; int rc; if ((rc = RegOpenKeyEx(HKEY_LOCAL_MACHINE, subkey.c_str(), 0, KEY_READ, &hkey)) == ERROR_SUCCESS) { RegCloseKey(hkey); switch ((int)(type&0x0c)) { case JDK: subkey.append(JDK_PATH); break; case JRE: subkey.append(JRE_PATH); break; } if ((rc = RegOpenKeyEx(HKEY_LOCAL_MACHINE, subkey.c_str(), 0, KEY_READ, &hkey)) == ERROR_SUCCESS) { String key = CURRENT_VERSION; String value = getRegValue(hkey, key, 0); result.insert(string_pair(key, value)); _TCHAR version[BUFF_SIZE]; for (int i = 0; ; i++) { buffSize = BUFF_SIZE; memset(version, BUFF_SIZE, sizeof(_TCHAR)); rc = RegEnumKeyEx(hkey, i, version, &buffSize, NULL, NULL, NULL, &ft); if (rc != ERROR_SUCCESS) { break; } vers.push_back(String((_TCHAR *)version)); } if (!vers.empty()) { switch (type&0x03) { case JavaHome: for (size_t i = 0; i < vers.size(); i++) { key = vers.at(i); if ((rc = RegOpenKeyEx(hkey, key.c_str(), 0, KEY_READ, &hVKey)) == ERROR_SUCCESS) { value = getRegValue(hVKey, String(_T("JavaHome")), 0); result.insert(string_pair(key, value)); RegCloseKey(hVKey); } } break; case RuntimeLib: for (size_t i = 0; i < vers.size(); i++) { key = vers.at(i); if ((rc = RegOpenKeyEx(hkey, key.c_str(), 0, KEY_READ, &hVKey)) == ERROR_SUCCESS) { value = getRegValue(hVKey, String(_T("RuntimeLib")), 0); result.insert(string_pair(key, value)); RegCloseKey(hVKey); } } break; } } RegCloseKey(hkey); } } return result; } /* * JNIのvfprintf処理にユーザ処理を加えるルーチンを登録します * param : ユーザ処理ルーチン(PrintRoutineアドレス) * * return : 無し */ void JvmEnv::setPrintRoutine(lpPrintRoutine routine) { print_routine = routine; } /* * JNIのabort処理にユーザ処理を加えるルーチンを登録します * param : ユーザ処理ルーチン(PrintRoutineアドレス) * * return : 無し */ void JvmEnv::setAbortRoutine(lpAbortRoutine routine) { abort_routine = routine; } /* * JNIのexit処理にユーザ処理を加えるルーチンを登録します * param : ユーザ処理ルーチン(ExitRoutineアドレス) * * return : 無し */ void JvmEnv::setExitRoutine(lpExitRoutine routine) { exit_routine = routine; } /* * 導入済みのJava情報から指定のパス情報を取得する * param : 確認するJavaのタイプ(int) * 取得したい情報(String) * * return : String */ String JvmEnv::findJvm(int type, bool version, String basic) { String result; string_map installed = installedJvm(type&0x0f); psmap item = installed.end(); switch (type&0xf0) { case CurrentVersion: item = installed.find(CURRENT_VERSION); if (item != installed.end()) { if (version) { result = item->second; } else { item = installed.find(item->second); if (item != installed.end()) result = item->second; } } break; case TargetVersion: for (psmap ent = installed.begin(); ent != installed.end(); ent++) { if (ent->first == basic) { if (version) { result = item->first; } else { result = item->second; } } } break; case LatestVersion: for (psmap ent = installed.begin(); ent != installed.end(); ent++) { String subkey = ent->first; if (subkey.compare(CURRENT_VERSION) == 0) { continue; } if (!basic.empty()) { if (subkey.compare(0, basic.length(), basic) != 0) { continue; } } if (item == installed.end()) { item = ent; } else { if (subkey.compare(item->first) > 0) { item = ent; } } } if (version) { result = item->first; } else { result = item->second; } break; } return result; }
JvmServiceクラスで実際にJavaのプログラムを呼び出します。
単にプログラムを呼び出して実行するだけじゃなくって、実行結果として数値(int)と文字列を取得できるように構築しました。
JvmService.h
#ifndef _JVM_SERVICE_CLASS #define _JVM_SERVICE_CLASS class JvmService { private: String jniClassPath(String original); public: JvmService(JvmEnv jvm_env); JvmService(const JvmService& from); ~JvmService(); void setCallClass(String main_class, String package = String()); String getCallClass(); int execute(); int end_wait(int wait_time = INFINITE); void result(); void setReturnCodeName(String name); int getReturnCode(); void setReturnMessageName(String name); String getReturnMessage(); static void WINAPI startApp(JvmService *svc); private: JvmEnv jvm_env; String main_class; HANDLE java_thread; String rc_field; int rc; String rm_field; String rm; }; // class JvmService #endif // _JVM_SERVICE_CLASS
JvmService.cpp
#include "jvmenv.h" #include "jvmservice.h" /* * パス分離記号の"."を"/"に変換する * param : パス(String) * * return : String */ String JvmService::jniClassPath(String original) { String path = original; size_t pos = path.find(_T('.')); do { if (pos != String::npos) { path.replace(pos++, 1, _T("/")); pos = path.find(_T('.'), pos); } } while (pos != String::npos); return path; } // Constructer JvmService::JvmService(JvmEnv jvm_env) { this->jvm_env = jvm_env; this->java_thread = NULL; this->rc = 0; } // Copy Constructer JvmService::JvmService(const JvmService& from) { jvm_env = from.jvm_env; main_class = from.main_class; java_thread = from.java_thread; rc_field = from.rc_field; rc = from.rc; rm_field = from.rm_field; rm = from.rm; } // Destructer JvmService::~JvmService() { } /* * 起動するJavaのクラスを設定する * param : クラス名(String) * パッケージ名(String) * * return : 無し */ void JvmService::setCallClass(String class_name, String package) { if (package.empty()) { main_class = class_name; } else { main_class = package; main_class.append(_T(".")); main_class.append(class_name); } } /* * 起動するJavaのクラスを取得する * param : クラス名(String) * パッケージ名(String) * * return : 無し */ String JvmService::getCallClass() { return jniClassPath(main_class); } /* * 設定したJavaのプログラムを起動する * param : 無し * * return : int */ int JvmService::execute() { java_thread = CreateThread(NULL, 4096, (LPTHREAD_START_ROUTINE)JvmService::startApp, (void *)this, 0, NULL); if (java_thread != NULL) { WaitForSingleObject(java_thread, 0); return 0; } return -1; } /* * Javaプログラムの終了を待つ * param : 待ち時間-秒(int) * * return : int */ int JvmService::end_wait(int wait_time) { unsigned long rc = 0; if (wait_time >= 0) rc = WaitForSingleObject(java_thread, wait_time*1000); else rc = WaitForSingleObject(java_thread, INFINITE); if (rc != WAIT_TIMEOUT) { CloseHandle(java_thread); return 0; } return -1; } /* * Javaの処理結果を取得する * param : 無し * * return : なし */ void JvmService::result() { JNIEnv *t_env; JavaVM *vm = jvm_env.getJvm(); if (vm->AttachCurrentThread((void**)&t_env, NULL) == JNI_OK) { jclass clazz = t_env->FindClass((const char *)_bstr_t((_TCHAR *)getCallClass().c_str())); if (clazz != NULL) { _bstr_t rc_str = _bstr_t((_TCHAR *)rc_field.c_str()); const char *rc_name = (const char *)rc_str; jfieldID rc_area = t_env->GetStaticFieldID(clazz, rc_name, "I"); if (t_env->ExceptionCheck() == JNI_TRUE) { if (t_env->ExceptionOccurred() != NULL) { t_env->ExceptionClear(); } } else { if (rc_area != NULL) { rc = (int)t_env->GetStaticIntField(clazz, rc_area); } } _bstr_t rm_str = _bstr_t((_TCHAR *)rm_field.c_str()); const char *rm_name = (const char *)rm_str; jfieldID rm_area = t_env->GetStaticFieldID(clazz, rm_name, "Ljava/lang/String;"); if (t_env->ExceptionCheck() == JNI_TRUE) { if (t_env->ExceptionOccurred() != NULL) { t_env->ExceptionClear(); } } else { if (rm_area != NULL) { jstring msg = (jstring)t_env->GetStaticObjectField(clazz, rm_area); const jchar *words = t_env->GetStringChars(msg, NULL); _bstr_t orginal = _bstr_t((wchar_t *)words); t_env->ReleaseStringChars(msg, words); rm = String((_TCHAR *)orginal); } } } vm->DetachCurrentThread(); } } /* * Javaの結果コードを取得するエリアの名前を設定する * param : エリアの名前(String) * * return : 無し */ void JvmService::setReturnCodeName(String name) { rc_field = name; } /* * Javaの結果コードを取得する * param : 無し * * return : int */ int JvmService::getReturnCode() { return rc; } /* * Javaの結果メッセージを取得するエリアの名前を設定する * param : エリアの名前(String) * * return : 無し */ void JvmService::setReturnMessageName(String name) { rm_field = name; } /* * Javaの結果メッセージを取得する * param : 無し * * return : String */ String JvmService::getReturnMessage() { return rm; } /* * Javaを呼び出す * param : 起動時に利用する情報(JvmServiceクラス) * * return : unsigned long */ void WINAPI JvmService::startApp(JvmService *svc) { JNIEnv *t_env; JavaVM *vm = svc->jvm_env.getJvm(); if (vm->AttachCurrentThread((void**)&t_env, NULL) == JNI_OK) { jclass clazz = t_env->FindClass((const char *)_bstr_t((_TCHAR *)svc->getCallClass().c_str())); if (clazz != NULL) { jmethodID mid = t_env->GetStaticMethodID(clazz, "main", "([Ljava/lang/String;)V"); if (mid != NULL) { jobjectArray ja = svc->jvm_env.jvmArgs(t_env); jthrowable tobj; t_env->CallStaticVoidMethod(clazz, mid, ja); if (t_env->ExceptionCheck() == JNI_TRUE) { if ((tobj = t_env->ExceptionOccurred()) != NULL) { t_env->ExceptionDescribe(); t_env->ExceptionClear(); } } } } vm->DetachCurrentThread(); } }
サンプルとして、ネットワークインターフェースの情報を取得するプログラムをこのクラスを使って起動するアプリケーションを作りました。
jnicall.cpp
#include <windows.h> #include <tchar.h> #include <iostream> #include <locale> #include <jvmenv.h> #include <jvmservice.h> int _tmain(int argc, _TCHAR* argv[]) { std::wcout.imbue(std::locale("japanese")); JvmEnv env; env.loadArgs(argc, argv); env.addJavaParam(String(_T("-Xms8m"))); env.addJavaParam(String(_T("-Xms16m"))); env.addJavaParam(String(_T("-client"))); env.addJavaParam(String(_T("-Djava.compiler=NONE"))); String latest = env.findJvm(JRERuntimeLib+LatestVersion, false); if (env.loadJLib(latest) == 0) { env.addClassPath(_T("c:\\java\\net\\classes")); if (env.createJvm() == 0) { JvmService service = JvmService(env); service.setCallClass(_T("IfInfoTest"), _T("net.test")); service.execute(); service.end_wait(); service.result(); std::wcout << _T("Execute result ") << service.getReturnCode() << _T(":") << service.getReturnMessage() << std::endl; env.destroyJvm(); } env.unloadJLib(); } return 0; }
結局サンプルプログラムがコンソールアプリケーションなのでちょっと変な感じですが、この部分はWindowsアプリケーションとして作ることも可能です。