From b11f3bc8e33232f0adbf3489ceae1b739b8699ba Mon Sep 17 00:00:00 2001 From: Will Dietz Date: Wed, 25 Apr 2018 19:42:35 -0500 Subject: [PATCH] cpython: don't use lchmod() on Linux, fix w/musl upstream issue: https://bugs.python.org/issue31940 There are two PR's proposed to fix this, but both seem to be stalling waiting for review. I previously used what appears to be the favored of the two approaches[1] to fix this, with plan of keeping it musl-only until PR was merged. However, while writing up a commit message explaining the problem and why it needed fixing... I investigated a bit and found it increasingly hard to justify anything other than ... simply not using lchmod. Here's what I found: * lchmod is non-POSIX, seems BSD-only these days * Functionality of lchmod isn't supported on Linux * best scenario on Linux would be an error * POSIX does provide lchmod-esque functionality with fchmodat(), which AFAICT is generally preferred. * Python intentionally overlooks fchmodat()[2] electing instead to use lchmod() behavior as a proxy for whether fchmodat() "works". I'm not sure I follow their reasoning... * both glibc and musl provide lchmod impls: * glibc returns ENOSYS "not implemented" * musl implements lchmod with fchmodat(), and so returns EOPNOTSUPP "op not supported" * Python doesn't expect EOPNOTSUPP from lchmod, since it's not valid on BSD's lchmod. * "configure" doesn't actually check lchmod usefully, instead checks for glibc preprocessor defines to indicate if the function is just a stub[3]; somewhat fittingly, if the magic macros are defined then the next line of the C source is "choke me", causing the compiler to trip, fall, and point a finger at whatever is near where it ends up. (somewhat amusing, but AFAIK effective way to get an error :P) I'm leaving out links to threads on mailing lists and such, but for now I hope I've convinced you (or to those reading commit history: explained my reasons) that this is a bit of a mess[4]. And so instead of making a big mess messier, and with hopes of never thinking about this again, I propose we simply tell Python "don't use lchmod" on Linux. [1] https://github.com/python/cpython/pull/4783 [2] https://github.com/python/cpython/blob/28453feaa8d88bbcbf6d834b1d5ca396d17265f2/Lib/os.py#L144 [3] https://github.com/python/cpython/blob/28453feaa8d88bbcbf6d834b1d5ca396d17265f2/configure#L2198 [4] Messes happen, no good intention goes unpunished :). --- pkgs/development/interpreters/python/cpython/2.7/default.nix | 5 ++++- pkgs/development/interpreters/python/cpython/3.4/default.nix | 5 ++++- pkgs/development/interpreters/python/cpython/3.5/default.nix | 5 ++++- pkgs/development/interpreters/python/cpython/3.6/default.nix | 5 ++++- 4 files changed, 16 insertions(+), 4 deletions(-) diff --git a/pkgs/development/interpreters/python/cpython/2.7/default.nix b/pkgs/development/interpreters/python/cpython/2.7/default.nix index 5c12d7cec55c..9d89e96383f5 100644 --- a/pkgs/development/interpreters/python/cpython/2.7/default.nix +++ b/pkgs/development/interpreters/python/cpython/2.7/default.nix @@ -140,7 +140,10 @@ let "ac_cv_computed_gotos=yes" "ac_cv_file__dev_ptmx=yes" "ac_cv_file__dev_ptc=yes" - ]; + ] + # Never even try to use lchmod on linux, + # don't rely on detecting glibc-isms. + ++ optional hostPlatform.isLinux "ac_cv_func_lchmod=no"; postConfigure = if hostPlatform.isCygwin then '' sed -i Makefile -e 's,PYTHONPATH="$(srcdir),PYTHONPATH="$(abs_srcdir),' diff --git a/pkgs/development/interpreters/python/cpython/3.4/default.nix b/pkgs/development/interpreters/python/cpython/3.4/default.nix index 0946f8743fbe..85c45a9d396f 100644 --- a/pkgs/development/interpreters/python/cpython/3.4/default.nix +++ b/pkgs/development/interpreters/python/cpython/3.4/default.nix @@ -96,7 +96,10 @@ in stdenv.mkDerivation { "--without-ensurepip" "--with-system-expat" "--with-system-ffi" - ]; + ] + # Never even try to use lchmod on linux, + # don't rely on detecting glibc-isms. + ++ optional stdenv.hostPlatform.isLinux "ac_cv_func_lchmod=no"; preConfigure = '' for i in /usr /sw /opt /pkg; do # improve purity diff --git a/pkgs/development/interpreters/python/cpython/3.5/default.nix b/pkgs/development/interpreters/python/cpython/3.5/default.nix index 22c55d302625..d67cc7286942 100644 --- a/pkgs/development/interpreters/python/cpython/3.5/default.nix +++ b/pkgs/development/interpreters/python/cpython/3.5/default.nix @@ -90,7 +90,10 @@ in stdenv.mkDerivation { "--without-ensurepip" "--with-system-expat" "--with-system-ffi" - ]; + ] + # Never even try to use lchmod on linux, + # don't rely on detecting glibc-isms. + ++ optional stdenv.hostPlatform.isLinux "ac_cv_func_lchmod=no"; preConfigure = '' for i in /usr /sw /opt /pkg; do # improve purity diff --git a/pkgs/development/interpreters/python/cpython/3.6/default.nix b/pkgs/development/interpreters/python/cpython/3.6/default.nix index 950a165a2f4a..ee9a0df9a8c4 100644 --- a/pkgs/development/interpreters/python/cpython/3.6/default.nix +++ b/pkgs/development/interpreters/python/cpython/3.6/default.nix @@ -113,7 +113,10 @@ in stdenv.mkDerivation { "ac_cv_computed_gotos=yes" "ac_cv_file__dev_ptmx=yes" "ac_cv_file__dev_ptc=yes" - ]; + ] + # Never even try to use lchmod on linux, + # don't rely on detecting glibc-isms. + ++ optional stdenv.hostPlatform.isLinux "ac_cv_func_lchmod=no"; preConfigure = '' for i in /usr /sw /opt /pkg; do # improve purity