|
1 | 1 | ## This file contains functionality related to the actual layout of the files |
2 | 2 | # on disk. Things like the name of where downloads are stored, and what |
3 | 3 | # environment variables must be updated to, etc... |
4 | | -import Base: convert, joinpath, show |
| 4 | +import Base: convert, joinpath, show, withenv |
5 | 5 | using SHA |
6 | 6 |
|
7 | 7 | export Prefix, bindir, libdir, includedir, logdir, activate, deactivate, |
@@ -92,33 +92,35 @@ joinpath(s::AbstractString, prefix::Prefix, args...) = joinpath(s, prefix.path, |
92 | 92 | convert(::Type{AbstractString}, prefix::Prefix) = prefix.path |
93 | 93 | show(io::IO, prefix::Prefix) = show(io, "Prefix($(prefix.path))") |
94 | 94 |
|
95 | | -""" |
96 | | - split_PATH(PATH::AbstractString = ENV["PATH"]) |
97 | 95 |
|
98 | | -Splits a string such as the `PATH` environment variable into a list of strings |
99 | | -according to the path separation rules for the current platform. |
100 | 96 | """ |
101 | | -function split_PATH(PATH::AbstractString = ENV["PATH"]) |
102 | | - @static if Sys.iswindows() |
103 | | - return split(PATH, ";") |
104 | | - else |
105 | | - return split(PATH, ":") |
106 | | - end |
107 | | -end |
| 97 | + withenv(f::Function, prefixes::Vector{Prefix}) |
108 | 98 |
|
| 99 | +Wrapper function designed to help executables find dynamic libraries and child |
| 100 | +binaries by wrapping PATH and (DY)LD_LIBRARY_PATH. |
109 | 101 | """ |
110 | | - join_PATH(PATH::Vector{AbstractString}) |
| 102 | +function withenv(f::Function, prefixes::Vector{Prefix}) |
| 103 | + # Join `dirs` to ENV[key], removing duplicates and nonexistent directories |
| 104 | + # as we go, normalizing directory names, splitting and joining by `sep`. |
| 105 | + function joinenv(key, dirs, sep) |
| 106 | + value = [dirs..., split(get(ENV, key, ""), sep)...] |
| 107 | + return join([abspath(d) for d in value if isdir(d)], sep) |
| 108 | + end |
| 109 | + # We're going to build up PATH and {DY,}LD_LIBRARY_PATH such that binaries |
| 110 | + # that use things from the given prefixes can function properly. |
| 111 | + sep = Sys.iswindows() ? ";" : ":" |
| 112 | + mapping = ["PATH" => joinenv("PATH", bindir.(prefixes), sep)] |
111 | 113 |
|
112 | | -Given a list of strings, return a joined string suitable for the `PATH` |
113 | | -environment variable appropriate for the current platform. |
114 | | -""" |
115 | | -function join_PATH(paths::Vector{S}) where S<:AbstractString |
116 | | - @static if Sys.iswindows() |
117 | | - return join(paths, ";") |
118 | | - else |
119 | | - return join(paths, ":") |
| 114 | + # {DY,}LD_LIBRARY_PATH only makes sense on non-windows |
| 115 | + if !Sys.iswindows() |
| 116 | + envname = Sys.isapple() ? "DYLD_LIBRARY_PATH" : "LD_LIBRARY_PATH" |
| 117 | + push!(mapping, envname => joinenv(envname, libdir.(prefixes), ":")) |
120 | 118 | end |
| 119 | + |
| 120 | + # Use withenv to apply the calculated environment mappings to f. |
| 121 | + return withenv(f, mapping...) |
121 | 122 | end |
| 123 | +withenv(f::Function, prefix::Prefix) = withenv(f, [prefix]) |
122 | 124 |
|
123 | 125 | """ |
124 | 126 | bindir(prefix::Prefix) |
@@ -161,56 +163,6 @@ function logdir(prefix::Prefix) |
161 | 163 | return joinpath(prefix, "logs") |
162 | 164 | end |
163 | 165 |
|
164 | | -""" |
165 | | - activate(prefix::Prefix) |
166 | | -
|
167 | | -Prepends paths to environment variables so that binaries and libraries are |
168 | | -available to Julia. |
169 | | -""" |
170 | | -function activate(prefix::Prefix) |
171 | | - # Add to PATH |
172 | | - paths = split_PATH() |
173 | | - if !(bindir(prefix) in paths) |
174 | | - prepend!(paths, [bindir(prefix)]) |
175 | | - end |
176 | | - ENV["PATH"] = join_PATH(paths) |
177 | | - |
178 | | - # Add to DL_LOAD_PATH |
179 | | - if !(libdir(prefix) in Libdl.DL_LOAD_PATH) |
180 | | - prepend!(Libdl.DL_LOAD_PATH, [libdir(prefix)]) |
181 | | - end |
182 | | - return nothing |
183 | | -end |
184 | | - |
185 | | -""" |
186 | | - activate(func::Function, prefix::Prefix) |
187 | | -
|
188 | | -Prepends paths to environment variables so that binaries and libraries are |
189 | | -available to Julia, calls the user function `func`, then `deactivate()`'s |
190 | | -the `prefix`` again. |
191 | | -""" |
192 | | -function activate(func::Function, prefix::Prefix) |
193 | | - activate(prefix) |
194 | | - func() |
195 | | - deactivate(prefix) |
196 | | -end |
197 | | - |
198 | | -""" |
199 | | - deactivate(prefix::Prefix) |
200 | | -
|
201 | | -Removes paths added to environment variables by `activate()` |
202 | | -""" |
203 | | -function deactivate(prefix::Prefix) |
204 | | - # Remove from PATH |
205 | | - paths = split_PATH() |
206 | | - filter!(p -> p != bindir(prefix), paths) |
207 | | - ENV["PATH"] = join_PATH(paths) |
208 | | - |
209 | | - # Remove from DL_LOAD_PATH |
210 | | - filter!(p -> p != libdir(prefix), Libdl.DL_LOAD_PATH) |
211 | | - return nothing |
212 | | -end |
213 | | - |
214 | 166 | """ |
215 | 167 | extract_platform_key(path::AbstractString) |
216 | 168 |
|
|
0 commit comments