Exemple #1
0
JL_DLLEXPORT void *jl_load_dynamic_library(const char *modname, unsigned flags, int throw_err)
{
    char path[PATHBUF];
    int i;
    uv_stat_t stbuf;
    void *handle;
    int abspath;
    // number of extensions to try — if modname already ends with the
    // standard extension, then we don't try adding additional extensions
    int n_extensions = endswith_extension(modname) ? 1 : N_EXTENSIONS;

    /*
      this branch returns handle of libjulia
    */
    if (modname == NULL) {
#ifdef _OS_WINDOWS_
        if (!GetModuleHandleExW(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT,
                                (LPCWSTR)(uintptr_t)(&jl_load_dynamic_library),
                                (HMODULE*)&handle)) {
            jl_error("could not load base module");
        }
#else
        Dl_info info;
        if (!dladdr((void*)(uintptr_t)&jl_load_dynamic_library, &info) || !info.dli_fname)
            jl_error("could not load base module");
        handle = dlopen(info.dli_fname, RTLD_NOW);
#endif
        goto done;
    }

    abspath = isabspath(modname);

    /*
      this branch permutes all base paths in DL_LOAD_PATH with all extensions
      note: skip when !jl_base_module to avoid UndefVarError(:DL_LOAD_PATH),
            and also skip for absolute paths
    */
    if (!abspath && jl_base_module != NULL) {
        jl_array_t *DL_LOAD_PATH = (jl_array_t*)jl_get_global(jl_base_module, jl_symbol("DL_LOAD_PATH"));
        if (DL_LOAD_PATH != NULL) {
            size_t j;
            for (j = 0; j < jl_array_len(DL_LOAD_PATH); j++) {
                char *dl_path = jl_string_data(jl_array_ptr_data(DL_LOAD_PATH)[j]);
                size_t len = strlen(dl_path);
                if (len == 0)
                    continue;
                for (i=0; i < n_extensions; i++) {
                    const char *ext = extensions[i];
                    path[0] = '\0';
                    if (dl_path[len-1] == PATHSEPSTRING[0])
                        snprintf(path, PATHBUF, "%s%s%s", dl_path, modname, ext);
                    else
                        snprintf(path, PATHBUF, "%s" PATHSEPSTRING "%s%s", dl_path, modname, ext);
                    handle = jl_dlopen(path, flags);
                    if (handle)
                        goto done;
                    // bail out and show the error if file actually exists
                    if (jl_stat(path, (char*)&stbuf) == 0)
                        goto notfound;
                }
            }
        }
    }

    // now fall back and look in default library paths, for all extensions
    for(i=0; i < n_extensions; i++) {
        const char *ext = extensions[i];
        path[0] = '\0';
        snprintf(path, PATHBUF, "%s%s", modname, ext);
        handle = jl_dlopen(path, flags);
        if (handle)
            goto done;
    }

notfound:
    if (throw_err) {
        const char * reason = jl_dlerror();
        jl_errorf("could not load library \"%s\"\n%s", modname, reason);
    }
    return NULL;

done:
    return handle;
}
Exemple #2
0
static void *jl_load_dynamic_library_(const char *modname, unsigned flags, int throw_err)
{
    char *ext;
    char path[PATHBUF];
    int i;
    uv_stat_t stbuf;
    void *handle;

/*
    this branch returns handle of libjulia
*/
    if (modname == NULL) {
#ifdef _OS_WINDOWS_
        if (!GetModuleHandleExW(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT,
                                (LPCWSTR)(&jl_load_dynamic_library),
                                (HMODULE*)&handle)) {
            jl_error("could not load base module");
        }
#else
        handle = dlopen(NULL, RTLD_NOW);
#endif
        goto done;
    }
/*
    this branch shortcuts absolute paths
*/
#ifdef _OS_WINDOWS_
    else if (modname[1] == ':') {
#else
    else if (modname[0] == '/') {
#endif
        handle = jl_dlopen(modname, flags);
        if (handle)
            goto done;
        // bail out and show the error if file actually exists
        if (jl_stat(modname, (char*)&stbuf) == 0)
            goto notfound;
    }
/*
    this branch permutes all base paths in DL_LOAD_PATH with all extensions
    note: skip when !jl_base_module to avoid UndefVarError(:DL_LOAD_PATH)
*/
    else if (jl_base_module != NULL) {
        jl_array_t *DL_LOAD_PATH = (jl_array_t*)jl_get_global(jl_base_module, jl_symbol("DL_LOAD_PATH"));
        if (DL_LOAD_PATH != NULL) {
            size_t j;
            for (j = 0; j < jl_array_len(DL_LOAD_PATH); j++) {
                char *dl_path = jl_string_data(jl_cell_data(DL_LOAD_PATH)[j]);
                size_t len = strlen(dl_path);
                if (len == 0)
                    continue;
                for(i=0; i < N_EXTENSIONS; i++) {
                    ext = extensions[i];
                    path[0] = '\0';
                    handle = NULL;
                    if (dl_path[len-1] == PATHSEPSTRING[0])
                        snprintf(path, PATHBUF, "%s%s%s", dl_path, modname, ext);
                    else
                        snprintf(path, PATHBUF, "%s" PATHSEPSTRING "%s%s", dl_path, modname, ext);
                    handle = jl_dlopen(path, flags);
                    if (handle)
                        goto done;
                    // bail out and show the error if file actually exists
                    if (jl_stat(path, (char*)&stbuf) == 0)
                        goto notfound;
                }
            }
        }
    }

    // now fall back and look in default library paths, for all extensions
    for(i=0; i < N_EXTENSIONS; i++) {
        ext = extensions[i];
        path[0] = '\0';
        handle = NULL;
        snprintf(path, PATHBUF, "%s%s", modname, ext);
        handle = jl_dlopen(path, flags);
        if (handle)
            goto done;
    }

#if defined(__linux__) || defined(__FreeBSD__)
// check map of versioned libs from "libX" to full soname "libX.so.ver"
    {
        const char *soname = jl_lookup_soname(modname, strlen(modname));
        if (soname) {
            handle = jl_dlopen(soname, flags);
            if (handle)
                goto done;
        }
    }
#endif

notfound:
    if (throw_err)
        jl_dlerror("could not load library \"%s\"\n%s", modname);
    return NULL;

done:
    return handle;
}

JL_DLLEXPORT void *jl_load_dynamic_library_e(const char *modname, unsigned flags)
{
    return jl_load_dynamic_library_(modname, flags, 0);
}

JL_DLLEXPORT void *jl_load_dynamic_library(const char *modname, unsigned flags)
{
    return jl_load_dynamic_library_(modname, flags, 1);
}

JL_DLLEXPORT void *jl_dlsym_e(void *handle, const char *symbol)
{
#ifdef _OS_WINDOWS_
    void *ptr = GetProcAddress((HMODULE) handle, symbol);
#else
    dlerror(); /* Reset error status. */
    void *ptr = dlsym(handle, symbol);
#endif
    return ptr;
}