Skip to content

Commit 80cd87f

Browse files
committed
unix: remove linking of libcrypt on CPython < 3.11
libcrypt.so again makes an unwanted appearance. It turns out CPython's configure up until 3.11 exhibited arguably buggy behavior where as part of searching for libcrypt it always added `-lcrypt` to LIBS, which got picked up by all linker invocations. Partially applying the upstream patch on CPython < 3.11 makes the problem go away. See also python/cpython#28881. Closes #197.
1 parent d77df80 commit 80cd87f

File tree

3 files changed

+36
-1
lines changed

3 files changed

+36
-1
lines changed

cpython-unix/build-cpython.sh

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -228,6 +228,13 @@ if [ -n "${PYTHON_MEETS_MINIMUM_VERSION_3_12}" ]; then
228228
patch -p1 -i ${ROOT}/patch-checksharedmods-disable.patch
229229
fi
230230

231+
# CPython < 3.11 always linked against libcrypt. We backport part of
232+
# upstream commit be21706f3760bec8bd11f85ce02ed6792b07f51f to avoid this
233+
# behavior.
234+
if [ -n "${PYTHON_MEETS_MAXIMUM_VERSION_3_10}" ]; then
235+
patch -p1 -i ${ROOT}/patch-configure-crypt-no-modify-libs.patch
236+
fi
237+
231238
# We patched configure.ac above. Reflect those changes.
232239
autoconf
233240

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
diff --git a/configure.ac b/configure.ac
2+
index ac3be3850a..b6e2144783 100644
3+
--- a/configure.ac
4+
+++ b/configure.ac
5+
@@ -4057,6 +4057,8 @@ AC_CHECK_FUNCS(setpgrp,
6+
7+
# We search for both crypt and crypt_r as one or the other may be defined
8+
# This gets us our -lcrypt in LIBS when required on the target platform.
9+
+# Save/restore LIBS to avoid linking libpython with libcrypt.
10+
+LIBS_SAVE=$LIBS
11+
AC_SEARCH_LIBS(crypt, crypt)
12+
AC_SEARCH_LIBS(crypt_r, crypt)
13+
14+
@@ -4071,6 +4073,7 @@ char *r = crypt_r("", "", &d);
15+
[AC_DEFINE(HAVE_CRYPT_R, 1, [Define if you have the crypt_r() function.])],
16+
[])
17+
)
18+
+LIBS=$LIBS_SAVE
19+
20+
AC_CHECK_FUNCS(clock_gettime, [], [
21+
AC_CHECK_LIB(rt, clock_gettime, [

src/validation.rs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,6 @@ const RECOGNIZED_TRIPLES: &[&str] = &[
6262
const ELF_ALLOWED_LIBRARIES: &[&str] = &[
6363
// LSB set.
6464
"libc.so.6",
65-
"libcrypt.so.1",
6665
"libdl.so.2",
6766
"libm.so.6",
6867
"libpthread.so.0",
@@ -864,6 +863,14 @@ fn validate_elf<'data, Elf: FileHeader<Endian = Endianness>>(
864863
python_major_minor
865864
));
866865

866+
// Allow the _crypt extension module - and only it - to link against libcrypt,
867+
// which is no longer universally present in Linux distros.
868+
if let Some(filename) = path.file_name() {
869+
if filename.to_string_lossy().starts_with("_crypt") {
870+
allowed_libraries.push("libcrypt.so.1".to_string());
871+
}
872+
}
873+
867874
let wanted_glibc_max_version = GLIBC_MAX_VERSION_BY_TRIPLE
868875
.get(target_triple)
869876
.expect("max glibc version not defined for target triple");

0 commit comments

Comments
 (0)