Index: vm/port/include/port_dso.h =================================================================== --- vm/port/include/port_dso.h (revision 547218) +++ vm/port/include/port_dso.h (working copy) @@ -88,6 +88,18 @@ uint32 mode, apr_pool_t* pool); +/** +* Returns full path to an executable or a library module, where +* symbol_address is located. +* @param symbol_address - address of the symbol to locate a module for +* @param[out] path - pointer to where to store path to a module +* @param[out] path_length - pointer to where to store path length +* @return APR_SUCCESS if OK; otherwise, an error code. +* @note You should first call this function with path +* equals to NULL to determine the length of modules full path. Then +* call with allocated buffer to get the path. +*/ +APR_DECLARE(apr_status_t) port_dso_get_library_location(void* symbol_address, char* path, uint32* path_length); /** * Returns the list of directories wher the OS searches for libraries. Index: vm/port/src/misc/linux/dso.c =================================================================== --- vm/port/src/misc/linux/dso.c (revision 547218) +++ vm/port/src/misc/linux/dso.c (working copy) @@ -14,11 +14,12 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -/** +/** * @author Alexey V. Varlamov * @version $Revision: 1.1.2.1.4.3 $ -*/ +*/ +#define _GNU_SOURCE #include #include #include @@ -53,6 +54,27 @@ } } +APR_DECLARE(apr_status_t) port_dso_get_library_location(void* symbol_address, + char* path, + uint32* path_length) +{ + Dl_info module_info; + + if(symbol_address == NULL || path_length == NULL) + return APR_BADARG; + + dladdr(symbol_address, &module_info); + + *path_length = strlen(module_info.dli_fname); + if(path != NULL) { + strncpy(path, module_info.dli_fname, *path_length); + path[*path_length] = '\0'; + } + + return APR_SUCCESS; +} + + APR_DECLARE(apr_status_t) port_dso_search_path(char** path, apr_pool_t* pool) { char* res = getenv("LD_LIBRARY_PATH"); Index: vm/port/src/misc/win/dso.c =================================================================== --- vm/port/src/misc/win/dso.c (revision 547218) +++ vm/port/src/misc/win/dso.c (working copy) @@ -79,7 +79,37 @@ return APR_SUCCESS; }*/ } - + +APR_DECLARE(apr_status_t) port_dso_get_library_location(void* symbol_address, + char* path, + uint32* path_length) +{ + HMODULE module; + DWORD length; + char module_name[MAX_PATH]; + + if(symbol_address == NULL || path_length == NULL) + return APR_BADARG; + + if(!GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, + (LPCTSTR)symbol_address, &module)) + { + return APR_FROM_OS_ERROR(GetLastError()); + } + length = GetModuleFileName(module, module_name, MAX_PATH); + if(length == 0) + return APR_FROM_OS_ERROR(GetLastError()); + + *path_length = length; + if(path != NULL) { + strncpy(path, module_name, *path_length); + path[*path_length] = '\0'; + } + + FreeLibrary(module); + return APR_SUCCESS; +} + APR_DECLARE(apr_status_t) port_dso_search_path(char** path, apr_pool_t* pool) { return apr_env_get(path, "PATH", pool); Index: vm/vmcore/src/init/vm_properties.cpp =================================================================== --- vm/vmcore/src/init/vm_properties.cpp (revision 547218) +++ vm/vmcore/src/init/vm_properties.cpp (working copy) @@ -43,57 +43,8 @@ // local memory pool for temporary allocation static apr_pool_t *prop_pool; -static const char *api_dll_files[] = -{ - "harmonyvm", - "hythr", - "hysig", - "hyprt", - "hyzlib", - "hytext", - "hynio", - "vmi", - "hyluni", - "hyarchive" -}; - #define GC_DLL "gc_gen" -/** - * Compose a string of file names each of them beginning with path, - * names separated by PORT_PATH_SEPARATOR. If patch is NULL, no path - * or separator will be prefixed - */ -static char *compose_full_files_path_names_list(const char *path, - const char **dll_names, - const int names_number, - bool is_dll) -{ - char* full_name = ""; - for (int iii = 0; iii < names_number; iii++) - { - const char *tmp = dll_names[iii]; - if (is_dll) { - tmp = port_dso_name_decorate(tmp, prop_pool); - } - - /* - * if the path is non-null, prefix, otherwise do nothing - * to avoid the problem of "/libfoo.so" when we don't want - * a path attached - */ - - if (path != NULL) { - tmp = port_filepath_merge(path, tmp, prop_pool); - } - - full_name = apr_pstrcat(prop_pool, full_name, tmp, - (iii + 1 < names_number) ? PORT_PATH_SEPARATOR_STR : "", NULL); - } - - return full_name; -} - static char* get_module_filename(void* code_ptr) { native_module_t* modules; @@ -261,26 +212,79 @@ properties.set_new("java.class.path", "."); } + +static void init_natives_path(Properties& properties) { + static const char* kernel_natives[] = { + "harmonyvm" + }; + + static const char* api_natives[] = + { + "hythr", + "hysig", + "hyprt", + "hyzlib", + "hytext", + "hynio", + "vmi", + "hyluni", + "hyarchive" + }; + + static const unsigned int n_api_natives = sizeof(api_natives) / sizeof(char *); + uint32 n_vm_loc; + port_dso_get_library_location((void*)initialize_properties, NULL, &n_vm_loc); + char* vm_location = (char*)STD_ALLOCA(n_vm_loc + 1); + port_dso_get_library_location((void*)initialize_properties, vm_location, &n_vm_loc); + + char* last_slash = strrchr(vm_location, PORT_FILE_SEPARATOR); + assert(last_slash); + *last_slash = '\0'; + assert(strlen(vm_location) > 0); // FIXME: should report deployment error + if(!properties.get(O_A_H_VM_VMDIR)) { + properties.set_new(O_A_H_VM_VMDIR, vm_location); + } + + char* full_paths = ""; + const char* tmp = kernel_natives[0]; + tmp = port_dso_name_decorate(tmp, prop_pool); + tmp = port_filepath_merge(vm_location, tmp, prop_pool); + full_paths = apr_pstrcat(prop_pool, full_paths, tmp, + PORT_PATH_SEPARATOR_STR, NULL); + + last_slash = strrchr(vm_location, PORT_FILE_SEPARATOR); + assert(last_slash); + *last_slash = '\0'; + assert(strlen(vm_location) > 0); // FIXME: should report deployment error + const char* api_location = vm_location; + + for (int iii = 0; iii < n_api_natives; iii++) + { + tmp = api_natives[iii]; + tmp = port_dso_name_decorate(tmp, prop_pool); + tmp = port_filepath_merge(api_location, tmp, prop_pool); + + full_paths = apr_pstrcat(prop_pool, full_paths, tmp, + (iii + 1 < n_api_natives) ? PORT_PATH_SEPARATOR_STR : "", NULL); + } + + properties.set_new("vm.other_natives_dlls", full_paths); +} + //vm part -static void init_vm_properties(Properties & properties) +static void init_vm_properties(Properties& properties) { - properties.set_new("vm.assert_dialog", "true"); - properties.set_new("vm.crash_handler", "false"); - properties.set_new("vm.finalize", "true"); - properties.set_new("vm.jit_may_inline_sync", "true"); - properties.set_new("vm.use_verifier", "true"); - properties.set_new("vm.jvmti.enabled", "false"); - properties.set_new("vm.jvmti.compiled_method_load.inlined", "false"); - properties.set_new("vm.bootclasspath.appendclasspath", "false"); - properties.set_new("vm.dlls", PORT_DSO_NAME(GC_DLL)); + properties.set_new("vm.assert_dialog", "true"); + properties.set_new("vm.crash_handler", "false"); + properties.set_new("vm.finalize", "true"); + properties.set_new("vm.jit_may_inline_sync", "true"); + properties.set_new("vm.use_verifier", "true"); + properties.set_new("vm.jvmti.enabled", "false"); + properties.set_new("vm.jvmti.compiled_method_load.inlined", "false"); + properties.set_new("vm.bootclasspath.appendclasspath", "false"); + properties.set_new("vm.dlls", PORT_DSO_NAME(GC_DLL)); - int n_api_dll_files = sizeof(api_dll_files) / sizeof(char *); - /* - * pass NULL for the pathname as we don't want - * any path pre-pended - */ - char* path_buf = compose_full_files_path_names_list(NULL, api_dll_files, n_api_dll_files, true); - properties.set_new("vm.other_natives_dlls", path_buf); + init_natives_path(properties); } void