Skip to content

Commit 07f132f

Browse files
authored
set JULIA_HOME to try point to the julia binary (#23525)
fix #14577
1 parent 943c8e5 commit 07f132f

File tree

5 files changed

+74
-16
lines changed

5 files changed

+74
-16
lines changed

examples/embedding/LocalModule.jl

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
__precompile__()
2+
module LocalModule
3+
4+
export myapp
5+
6+
function myapp()
7+
p = addprocs(1)
8+
@everywhere p println("Taking over the world...")
9+
rmprocs(p)
10+
nothing
11+
end
12+
13+
end

examples/embedding/Makefile

+8-1
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,14 @@ $(BIN)/embedding$(EXE): $(SRCDIR)/embedding.c
3838
$(BIN)/embedding-debug$(EXE): $(SRCDIR)/embedding.c
3939
$(CC) $^ -o $@ $(CPPFLAGS_ADD) $(CPPFLAGS) $(CFLAGS_ADD) $(CFLAGS) $(LDFLAGS_ADD) $(LDFLAGS) $(DEBUGFLAGS)
4040

41-
check: $(BIN)/embedding$(EXE)
41+
ifneq ($(abspath $(BIN)),$(abspath $(SRCDIR)))
42+
# for demonstration purposes, our demo code is also installed
43+
# in $BIN, although this would likely not be typical
44+
$(BIN)/LocalModule.jl: $(SRCDIR)/LocalModule.jl
45+
cp $< $@
46+
endif
47+
48+
check: $(BIN)/embedding$(EXE) $(BIN)/LocalModule.jl
4249
$(JULIA) $(SRCDIR)/embedding-test.jl $<
4350
@echo SUCCESS
4451

examples/embedding/embedding-test.jl

+2-1
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,9 @@ end
2020
@test stderr == "MethodError: no method matching this_function_has_no_methods()\n"
2121
@test success(p)
2222
lines = wait(stdout_task)
23-
@test length(lines) == 9
23+
@test length(lines) == 10
2424
@test parse(Float64, lines[1]) sqrt(2)
2525
@test lines[8] == "called bar"
2626
@test lines[9] == "calling new bar"
27+
@test lines[10] == "\tFrom worker 2:\tTaking over the world..."
2728
end

examples/embedding/embedding.c

+19
Original file line numberDiff line numberDiff line change
@@ -149,6 +149,25 @@ int main()
149149
bar();
150150
}
151151

152+
{
153+
// Importing a Julia package
154+
155+
checked_eval_string("let d = dirname(unsafe_string(Base.JLOptions().julia_bin))\n"
156+
// disable the package manager
157+
" ENV[\"JULIA_PKGDIR\"] = joinpath(d, \"disabled\")\n"
158+
// locate files relative to the "embedding" executable
159+
" empty!(LOAD_PATH)\n"
160+
" push!(LOAD_PATH, d)\n"
161+
// this directory needs to be writable for the example,
162+
// although in real code it usually wouldn't necessarily be used that way
163+
" empty!(Base.LOAD_CACHE_PATH)\n"
164+
" push!(Base.LOAD_CACHE_PATH, tempdir())\n"
165+
"end");
166+
checked_eval_string("import LocalModule");
167+
checked_eval_string("LocalModule.myapp()");
168+
}
169+
170+
152171
int ret = 0;
153172
jl_atexit_hook(ret);
154173
return ret;

src/jlapi.c

+32-14
Original file line numberDiff line numberDiff line change
@@ -26,19 +26,24 @@ JL_DLLEXPORT char * __cdecl dirname(char *);
2626
#else
2727
#include <libgen.h>
2828
#endif
29+
#ifndef _OS_WINDOWS_
30+
#include <dlfcn.h>
31+
#endif
2932

30-
JL_DLLEXPORT int jl_is_initialized(void) { return jl_main_module!=NULL; }
33+
JL_DLLEXPORT int jl_is_initialized(void)
34+
{
35+
return jl_main_module != NULL;
36+
}
3137

32-
// First argument is the usr/lib directory where libjulia is, or NULL to guess.
33-
// if that doesn't work, try the full path to the "lib" directory that
34-
// contains lib/julia/sys.ji
38+
// First argument is the usr/bin directory where the julia binary is, or NULL to guess.
3539
// Second argument is the path of a system image file (*.ji) relative to the
36-
// first argument path, or relative to the default julia home dir. The default
37-
// is something like ../lib/julia/sys.ji
40+
// first argument path, or relative to the default julia home dir.
41+
// The default is something like ../lib/julia/sys.ji
3842
JL_DLLEXPORT void jl_init_with_image(const char *julia_home_dir,
3943
const char *image_relative_path)
4044
{
41-
if (jl_is_initialized()) return;
45+
if (jl_is_initialized())
46+
return;
4247
libsupport_init();
4348
jl_options.julia_home = julia_home_dir;
4449
if (image_relative_path != NULL)
@@ -51,17 +56,30 @@ JL_DLLEXPORT void jl_init_with_image(const char *julia_home_dir,
5156

5257
JL_DLLEXPORT void jl_init(void)
5358
{
54-
char *libjldir = NULL;
55-
59+
char *libbindir = NULL;
60+
#ifdef _OS_WINDOWS_
5661
void *hdl = (void*)jl_load_dynamic_library_e(NULL, JL_RTLD_DEFAULT);
57-
if (hdl)
58-
libjldir = dirname((char*)jl_pathname_for_handle(hdl));
59-
if (libjldir)
60-
jl_init_with_image(libjldir, jl_get_default_sysimg_path());
61-
else {
62+
if (hdl) {
63+
char *to_free = (char*)jl_pathname_for_handle(hdl);
64+
if (to_free) {
65+
libbindir = strdup(dirname(to_free));
66+
free(to_free);
67+
}
68+
}
69+
#else
70+
Dl_info dlinfo;
71+
if (dladdr((void*)jl_init, &dlinfo) != 0 && dlinfo.dli_fname) {
72+
char *to_free = strdup(dlinfo.dli_fname);
73+
(void)asprintf(&libbindir, "%s" PATHSEPSTRING ".." PATHSEPSTRING "%s", dirname(to_free), "bin");
74+
free(to_free);
75+
}
76+
#endif
77+
if (!libbindir) {
6278
printf("jl_init unable to find libjulia!\n");
6379
abort();
6480
}
81+
jl_init_with_image(libbindir, jl_get_default_sysimg_path());
82+
free(libbindir);
6583
}
6684

6785
JL_DLLEXPORT jl_value_t *jl_eval_string(const char *str)

0 commit comments

Comments
 (0)