Skip to content

Commit 4a5a1fe

Browse files
committed
fail loudly when tbb libraries cannot be versioned
1 parent d7be8ab commit 4a5a1fe

1 file changed

Lines changed: 63 additions & 29 deletions

File tree

src/install.libs.R

Lines changed: 63 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -167,39 +167,73 @@ versionBundledTbbLibraries <- function(tbbDest) {
167167
suffix <- "2"
168168

169169
libs <- list.files(tbbDest, pattern = "^libtbb.*\\.so$", full.names = TRUE)
170-
for (lib in libs) {
171-
172-
# leave symlinks and linker scripts (i.e. an already-versioned layout)
173-
# untouched; only real, unversioned libraries need renaming
174-
if (nzchar(Sys.readlink(lib)))
175-
next
176-
177-
versioned <- paste0(lib, ".", suffix)
178-
if (file.exists(versioned))
179-
next
180-
181-
fmt <- "** versioning tbb library '%s' -> '%s'"
182-
msg <- sprintf(fmt, basename(lib), basename(versioned))
183-
writeLines(msg)
184-
185-
# 'libtbb.so' -> 'libtbb.so.2', then re-create 'libtbb.so' as a
186-
# relative symlink pointing back at the versioned library
187-
file.rename(lib, versioned)
188-
linked <- tryCatch(
189-
file.symlink(basename(versioned), lib),
190-
warning = function(w) FALSE
191-
)
170+
for (lib in libs)
171+
versionBundledTbbLibrary(lib, paste0(lib, ".", suffix))
192172

193-
# if the symlink couldn't be created (e.g. a filesystem without symlink
194-
# support), fall back to a plain copy so that 'libtbb.so' still exists --
195-
# RcppParallel's own shared object records a load-time dependency on it
196-
if (!isTRUE(linked)) {
197-
writeLines("** could not create symlink; copying instead")
198-
file.copy(versioned, lib, overwrite = TRUE)
199-
}
173+
}
200174

175+
# Version a single bundled TBB library. Failing to produce the versioned
176+
# layout is an error: a partial or silently-skipped layout would only
177+
# resurface later as load failures in downstream binaries, so fail the
178+
# install loudly instead.
179+
versionBundledTbbLibrary <- function(lib, versioned) {
180+
181+
# leave symlinks (i.e. an already-versioned layout) untouched; only real,
182+
# unversioned libraries need renaming
183+
if (nzchar(Sys.readlink(lib)))
184+
return(invisible(FALSE))
185+
186+
# only version actual ELF libraries; this leaves linker scripts alone
187+
# (in old-style layouts, 'libtbb.so' is an INPUT() script and the real
188+
# library already sits at 'libtbb.so.2'), while still replacing a stale
189+
# 'libtbb.so.2' left behind by a previous installation
190+
if (!isElfFile(lib))
191+
return(invisible(FALSE))
192+
193+
fmt <- "** versioning tbb library '%s' -> '%s'"
194+
msg <- sprintf(fmt, basename(lib), basename(versioned))
195+
writeLines(msg)
196+
197+
# 'libtbb.so' -> 'libtbb.so.2'
198+
if (!isTRUE(file.rename(lib, versioned))) {
199+
fmt <- "couldn't rename '%s' to '%s'"
200+
stop(sprintf(fmt, lib, versioned))
201201
}
202202

203+
# re-create 'libtbb.so' as a relative symlink pointing back at the
204+
# versioned library
205+
linked <- tryCatch(
206+
file.symlink(basename(versioned), lib),
207+
warning = function(w) FALSE
208+
)
209+
if (isTRUE(linked))
210+
return(invisible(TRUE))
211+
212+
# if the symlink couldn't be created (e.g. a filesystem without symlink
213+
# support), fall back to a plain copy so that 'libtbb.so' still exists.
214+
# the library has already been renamed at this point, so a failed copy
215+
# would leave no 'libtbb.so' at all; fail loudly rather than complete a
216+
# broken install
217+
writeLines("** couldn't create symlink; copying instead")
218+
copied <- tryCatch(
219+
file.copy(versioned, lib, overwrite = TRUE),
220+
warning = function(w) FALSE
221+
)
222+
if (!isTRUE(copied)) {
223+
fmt <- "couldn't copy '%s' to '%s'"
224+
stop(sprintf(fmt, versioned, lib))
225+
}
226+
227+
invisible(TRUE)
228+
229+
}
230+
231+
isElfFile <- function(path) {
232+
header <- tryCatch(
233+
readBin(path, "raw", n = 4L),
234+
condition = function(cnd) raw()
235+
)
236+
identical(header, charToRaw("\x7fELF"))
203237
}
204238

205239
# Report which TBB libraries are about to be installed, and from where.

0 commit comments

Comments
 (0)