@@ -30,6 +30,54 @@ function _atpyexit()
30
30
return
31
31
end
32
32
33
+ # By default, ensure libstdc++ in the Conda environment is compatible with
34
+ # the one linked in Julia. This is platform/version dependent, so needs to
35
+ # occur at runtime.
36
+ #
37
+ # Allow the user to override the default. This is useful when the version
38
+ # of libstdcxx linked in Julia is customized in the local installation of
39
+ # Julia.
40
+ #
41
+ # To figure out cxx_version for a given Julia version, run
42
+ # strings /path/to/julia/lib/julia/libstdc++.so.6 | grep GLIBCXX
43
+ # then look at
44
+ # https://gcc.gnu.org/onlinedocs/gcc-12.1.0/libstdc++/manual/manual/abi.html
45
+ # for the highest GCC version compatible with the highest GLIBCXX version.
46
+ function get_libstdcxx_version_bound ()
47
+ # This list comes from: https://gcc.gnu.org/onlinedocs/libstdc++/manual/abi.html
48
+ # Start with GCC 4.8, as it's extremely difficult to build Julia with anything older
49
+ vers_mapping = Dict (
50
+ 18 => v " 4.8.0" ,
51
+ 19 => v " 4.8.3" ,
52
+ 20 => v " 4.9.0" ,
53
+ 21 => v " 5.1.0" ,
54
+ 22 => v " 6.1.0" ,
55
+ 23 => v " 7.1.0" ,
56
+ 24 => v " 7.2.0" ,
57
+ 25 => v " 8.1.0" ,
58
+ 26 => v " 9.1.0" ,
59
+ 27 => v " 9.2.0" ,
60
+ 28 => v " 9.5.0" ,
61
+ 29 => v " 11.3.0" ,
62
+ 30 => v " 12.2.0" ,
63
+ 31 => v " 13.1.0" ,
64
+ )
65
+ # Get the libstdcxx version that is currently loaded in this Julia process
66
+ loaded_libstdcxx_version = Base. BinaryPlatforms. detect_libstdcxx_version ()
67
+
68
+ if loaded_libstdcxx_version != = nothing
69
+ # Map it through to get a GCC version; if the version is unknown, we simply return
70
+ # the highest GCC version we know about, which should be a fairly safe choice.
71
+ max_version = get (vers_mapping, loaded_libstdcxx_version. patch, vers_mapping[maximum (keys (vers_mapping))])
72
+ return get (ENV , " JULIA_PYTHONCALL_LIBSTDCXX_VERSION_BOUND" , " >=3.4,<=$(max_version. major) .$(max_version. minor) " )
73
+ elseif haskey (ENV , " JULIA_PYTHONCALL_LIBSTDCXX_VERSION_BOUND" )
74
+ return ENV [" JULIA_PYTHONCALL_LIBSTDCXX_VERSION_BOUND" ]
75
+ else
76
+ # Julia does not link against any version of libstdc++ known to Julia (e.g. using clang instead, or something not in the 3.4.x series)
77
+ return nothing
78
+ end
79
+ end
80
+
33
81
function init_context ()
34
82
35
83
CTX. is_embedded = haskey (ENV , " JULIA_PYTHONCALL_LIBPTR" )
@@ -60,24 +108,12 @@ function init_context()
60
108
exe_path:: String
61
109
else
62
110
if Sys. islinux ()
63
- # Ensure libstdc++ in the Conda environment is compatible with the one
64
- # linked in Julia. This is platform/version dependent, so needs to occur at
65
- # runtime.
66
- #
67
- # To figure out cxx_version for a given Julia version, run
68
- # strings /path/to/julia/lib/julia/libstdc++.so.6 | grep GLIBCXX
69
- # then look at
70
- # https://gcc.gnu.org/onlinedocs/gcc-12.1.0/libstdc++/manual/manual/abi.html
71
- # for the highest GCC version compatible with the highest GLIBCXX version.
72
- if Base. VERSION <= v " 1.6.2"
73
- # GLIBCXX_3.4.26
74
- cxx_version = " >=3.4,<9.2"
75
- else
76
- # GLIBCXX_3.4.29
77
- # checked up to v1.8.0
78
- cxx_version = " >=3.4,<11.4"
111
+ cxx_version = get_libstdcxx_version_bound ()
112
+ if cxx_version != = nothing
113
+ CondaPkg. add (" libstdcxx-ng" , version= cxx_version, channel= " conda-forge" , temp= true , file= joinpath (@__DIR__ , " .." , " .." , " CondaPkg.toml" ), resolve= false )
79
114
end
80
- CondaPkg. add (" libstdcxx-ng" , version= cxx_version, channel= " conda-forge" , temp= true , file= joinpath (@__DIR__ , " .." , " .." , " CondaPkg.toml" ), resolve= false )
115
+ # if cxx_version is nothing, then we assume that Julia does not link against any version ob libstdc++ known by Julia, and so we do not
116
+ # enforce a version bound.
81
117
end
82
118
# By default, we use Python installed by CondaPkg.
83
119
exe_path = Sys. iswindows () ? joinpath (CondaPkg. envdir (), " python.exe" ) : joinpath (CondaPkg. envdir (), " bin" , " python" )
0 commit comments