Skip to content

Commit 1e7db24

Browse files
matejcikstratakis
authored andcommitted
bpo-1294959: Better support for systems with /usr/lib64
This introduces a new configure and sysconfig variable `platsubdir`, which is the name of subdirectory of $prefix that holds platform-specific libraries. On many Linux distributions, there is separation between /usr/lib and /usr/lib64, which was causing some problems due to the way Python manages its install paths. Now, platsubdir is used to select the appropriate lib directory.
1 parent 0d4f435 commit 1e7db24

File tree

12 files changed

+96
-28
lines changed

12 files changed

+96
-28
lines changed

Lib/distutils/command/install.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@
3030
INSTALL_SCHEMES = {
3131
'unix_prefix': {
3232
'purelib': '$base/lib/python$py_version_short/site-packages',
33-
'platlib': '$platbase/lib/python$py_version_short/site-packages',
33+
'platlib': '$platbase/$platsubdir/python$py_version_short/site-packages',
3434
'headers': '$base/include/python$py_version_short$abiflags/$dist_name',
3535
'scripts': '$base/bin',
3636
'data' : '$base',
@@ -281,7 +281,7 @@ def finalize_options(self):
281281
# about needing recursive variable expansion (shudder).
282282

283283
py_version = sys.version.split()[0]
284-
(prefix, exec_prefix) = get_config_vars('prefix', 'exec_prefix')
284+
(prefix, exec_prefix, platsubdir) = get_config_vars('prefix', 'exec_prefix', 'platsubdir')
285285
try:
286286
abiflags = sys.abiflags
287287
except AttributeError:
@@ -298,6 +298,7 @@ def finalize_options(self):
298298
'sys_exec_prefix': exec_prefix,
299299
'exec_prefix': exec_prefix,
300300
'abiflags': abiflags,
301+
'platsubdir': platsubdir,
301302
}
302303

303304
if HAS_USER_SITE:

Lib/distutils/sysconfig.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -146,8 +146,9 @@ def get_python_lib(plat_specific=0, standard_lib=0, prefix=None):
146146
prefix = plat_specific and EXEC_PREFIX or PREFIX
147147

148148
if os.name == "posix":
149+
libdir = plat_specific and get_config_var("platsubdir") or "lib"
149150
libpython = os.path.join(prefix,
150-
"lib", "python" + get_python_version())
151+
libdir, "python" + get_python_version())
151152
if standard_lib:
152153
return libpython
153154
else:

Lib/pydoc.py

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@ class or function within a module or module in a package. If the
6666
import platform
6767
import re
6868
import sys
69+
import sysconfig
6970
import time
7071
import tokenize
7172
import urllib.parse
@@ -392,9 +393,7 @@ def fail(self, object, name=None, *args):
392393

393394
docmodule = docclass = docroutine = docother = docproperty = docdata = fail
394395

395-
def getdocloc(self, object,
396-
basedir=os.path.join(sys.base_exec_prefix, "lib",
397-
"python%d.%d" % sys.version_info[:2])):
396+
def getdocloc(self, object, basedir=sysconfig.get_path('stdlib')):
398397
"""Return the location of module docs or None"""
399398

400399
try:

Lib/site.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -335,9 +335,15 @@ def getsitepackages(prefixes=None):
335335
seen.add(prefix)
336336

337337
if os.sep == '/':
338-
sitepackages.append(os.path.join(prefix, "lib",
338+
from sysconfig import get_config_var
339+
platsubdir = get_config_var("platsubdir")
340+
sitepackages.append(os.path.join(prefix, platsubdir,
339341
"python%d.%d" % sys.version_info[:2],
340342
"site-packages"))
343+
if platsubdir != "lib":
344+
sitepackages.append(os.path.join(prefix, "lib",
345+
"python%d.%d" % sys.version_info[:2],
346+
"site-packages"))
341347
else:
342348
sitepackages.append(prefix)
343349
sitepackages.append(os.path.join(prefix, "lib", "site-packages"))

Lib/sysconfig.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,10 +20,10 @@
2020

2121
_INSTALL_SCHEMES = {
2222
'posix_prefix': {
23-
'stdlib': '{installed_base}/lib/python{py_version_short}',
24-
'platstdlib': '{platbase}/lib/python{py_version_short}',
23+
'stdlib': '{installed_base}/{platsubdir}/python{py_version_short}',
24+
'platstdlib': '{platbase}/{platsubdir}/python{py_version_short}',
2525
'purelib': '{base}/lib/python{py_version_short}/site-packages',
26-
'platlib': '{platbase}/lib/python{py_version_short}/site-packages',
26+
'platlib': '{platbase}/{platsubdir}/python{py_version_short}/site-packages',
2727
'include':
2828
'{installed_base}/include/python{py_version_short}{abiflags}',
2929
'platinclude':

Lib/test/test_site.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -266,8 +266,9 @@ def test_getsitepackages(self):
266266
dirs = site.getsitepackages()
267267
if os.sep == '/':
268268
# OS X, Linux, FreeBSD, etc
269-
self.assertEqual(len(dirs), 1)
270-
wanted = os.path.join('xoxo', 'lib',
269+
platsubdir = sysconfig.get_config_var('platsubdir')
270+
self.assertTrue(len(dirs) in (1,2))
271+
wanted = os.path.join('xoxo', platsubdir,
271272
'python%d.%d' % sys.version_info[:2],
272273
'site-packages')
273274
self.assertEqual(dirs[0], wanted)

Lib/test/test_sysconfig.py

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -243,6 +243,7 @@ def test_user_similar(self):
243243
# is similar to the global posix_prefix one
244244
base = get_config_var('base')
245245
user = get_config_var('userbase')
246+
platsubdir = get_config_var("platsubdir")
246247
# the global scheme mirrors the distinction between prefix and
247248
# exec-prefix but not the user scheme, so we have to adapt the paths
248249
# before comparing (issue #9100)
@@ -257,8 +258,19 @@ def test_user_similar(self):
257258
# before comparing
258259
global_path = global_path.replace(sys.base_prefix, sys.prefix)
259260
base = base.replace(sys.base_prefix, sys.prefix)
261+
262+
if platsubdir != "lib":
263+
platbase = os.path.join(base, platsubdir)
264+
purebase = os.path.join(base, "lib")
265+
userlib = os.path.join(user, "lib")
266+
# replace platbase first because usually purebase is a prefix of platbase
267+
# /usr/lib is prefix of /usr/lib64 and would get replaced first
268+
modified_path = global_path.replace(platbase, userlib, 1).replace(purebase, userlib, 1)
269+
else:
270+
modified_path = global_path.replace(base, user, 1)
271+
260272
user_path = get_path(name, 'posix_user')
261-
self.assertEqual(user_path, global_path.replace(base, user, 1))
273+
self.assertEqual(user_path, modified_path)
262274

263275
def test_main(self):
264276
# just making sure _main() runs and returns things in the stdout

Lib/trace.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@
5252
import linecache
5353
import os
5454
import sys
55+
import sysconfig
5556
import token
5657
import tokenize
5758
import inspect
@@ -660,9 +661,8 @@ def main():
660661
opts = parser.parse_args()
661662

662663
if opts.ignore_dir:
663-
rel_path = 'lib', 'python{0.major}.{0.minor}'.format(sys.version_info)
664-
_prefix = os.path.join(sys.base_prefix, *rel_path)
665-
_exec_prefix = os.path.join(sys.base_exec_prefix, *rel_path)
664+
_prefix = sysconfig.get_path("stdlib")
665+
_exec_prefix = sysconfig.get_path("platstdlib")
666666

667667
def parse_ignore_dir(s):
668668
s = os.path.expanduser(os.path.expandvars(s))

Makefile.pre.in

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -137,13 +137,16 @@ exec_prefix= @exec_prefix@
137137
# Install prefix for data files
138138
datarootdir= @datarootdir@
139139

140+
# Name of "lib" directory under prefix
141+
platsubdir= @platsubdir@
142+
140143
# Expanded directories
141144
BINDIR= @bindir@
142145
LIBDIR= @libdir@
143146
MANDIR= @mandir@
144147
INCLUDEDIR= @includedir@
145148
CONFINCLUDEDIR= $(exec_prefix)/include
146-
SCRIPTDIR= $(prefix)/lib
149+
SCRIPTDIR= @libdir@
147150
ABIFLAGS= @ABIFLAGS@
148151

149152
# Detailed destination directories
@@ -752,6 +755,7 @@ Modules/getpath.o: $(srcdir)/Modules/getpath.c Makefile
752755
-DEXEC_PREFIX='"$(exec_prefix)"' \
753756
-DVERSION='"$(VERSION)"' \
754757
-DVPATH='"$(VPATH)"' \
758+
-DPLATSUBDIR='"$(platsubdir)"' \
755759
-o $@ $(srcdir)/Modules/getpath.c
756760

757761
Programs/python.o: $(srcdir)/Programs/python.c

Modules/getpath.c

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -55,9 +55,10 @@
5555
* pybuilddir.txt. If the landmark is found, we're done.
5656
*
5757
* For the remaining steps, the prefix landmark will always be
58-
* lib/python$VERSION/os.py and the exec_prefix will always be
59-
* lib/python$VERSION/lib-dynload, where $VERSION is Python's version
60-
* number as supplied by the Makefile. Note that this means that no more
58+
* $lib/python$VERSION/os.py and the exec_prefix will always be
59+
* $lib/python$VERSION/lib-dynload, where $VERSION is Python's version
60+
* number and $lib is PLATSUBDIR as supplied by the Makefile. (usually
61+
* "lib", "lib32" or "lib64"). Note that this means that no more
6162
* build directory checking is performed; if the first step did not find
6263
* the landmarks, the assumption is that python is running from an
6364
* installed setup.
@@ -86,7 +87,7 @@
8687
* containing the shared library modules is appended. The environment
8788
* variable $PYTHONPATH is inserted in front of it all. Finally, the
8889
* prefix and exec_prefix globals are tweaked so they reflect the values
89-
* expected by other code, by stripping the "lib/python$VERSION/..." stuff
90+
* expected by other code, by stripping the "$lib/python$VERSION/..." stuff
9091
* off. If either points to the build directory, the globals are reset to
9192
* the corresponding preprocessor variables (so sys.prefix will reflect the
9293
* installation location, even though sys.path points into the build
@@ -105,8 +106,8 @@ extern "C" {
105106
#endif
106107

107108

108-
#if !defined(PREFIX) || !defined(EXEC_PREFIX) || !defined(VERSION) || !defined(VPATH)
109-
#error "PREFIX, EXEC_PREFIX, VERSION, and VPATH must be constant defined"
109+
#if !defined(PREFIX) || !defined(EXEC_PREFIX) || !defined(VERSION) || !defined(VPATH) || !defined(PLATSUBDIR)
110+
#error "PREFIX, EXEC_PREFIX, VERSION, VPATH and PLATSUBDIR must be constant defined"
110111
#endif
111112

112113
#ifndef LANDMARK
@@ -1145,7 +1146,7 @@ calculate_init(PyCalculatePath *calculate,
11451146
if (!calculate->prefix) {
11461147
return DECODE_LOCALE_ERR("EXEC_PREFIX define", len);
11471148
}
1148-
calculate->lib_python = Py_DecodeLocale("lib/python" VERSION, &len);
1149+
calculate->lib_python = Py_DecodeLocale(PLATSUBDIR "/python" VERSION, &len);
11491150
if (!calculate->lib_python) {
11501151
return DECODE_LOCALE_ERR("EXEC_PREFIX define", len);
11511152
}

configure

Lines changed: 31 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -631,6 +631,7 @@ SRCDIRS
631631
THREADHEADERS
632632
LIBPL
633633
PY_ENABLE_SHARED
634+
platsubdir
634635
LIBPYTHON
635636
EXT_SUFFIX
636637
ALT_SOABI
@@ -841,6 +842,7 @@ with_dtrace
841842
with_libm
842843
with_libc
843844
enable_big_digits
845+
with_custom_platsubdir
844846
with_computed_gotos
845847
with_ensurepip
846848
with_openssl
@@ -1537,6 +1539,10 @@ Optional Packages:
15371539
--with(out)-dtrace disable/enable DTrace support
15381540
--with-libm=STRING math library
15391541
--with-libc=STRING C library
1542+
--with-custom-platsubdir=<libdirname>
1543+
name of the platform-specific lib subdirectory of
1544+
$prefix. This is usually "lib", "lib32" or "lib64".
1545+
Defaults to basename($libdir)
15401546
--with(out)-computed-gotos
15411547
Use computed gotos in evaluation loop (enabled by
15421548
default on supported compilers)
@@ -15179,11 +15185,34 @@ else
1517915185
LIBPYTHON=''
1518015186
fi
1518115187

15188+
# platsubdir must be defined before LIBPL definition
15189+
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for custom platsubdir" >&5
15190+
$as_echo_n "checking for custom platsubdir... " >&6; }
15191+
15192+
# Check whether --with-custom-platsubdir was given.
15193+
if test "${with_custom_platsubdir+set}" = set; then :
15194+
withval=$with_custom_platsubdir;
15195+
else
15196+
with_custom_platsubdir=yes
15197+
fi
15198+
15199+
case $with_custom_platsubdir in #(
15200+
yes) :
15201+
platsubdir=`basename ${libdir}` ;; #(
15202+
no) :
15203+
platsubdir=lib ;; #(
15204+
*) :
15205+
platsubdir=$with_custom_platsubdir ;;
15206+
esac
15207+
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $platsubdir" >&5
15208+
$as_echo "$platsubdir" >&6; }
15209+
15210+
1518215211

1518315212
if test x$PLATFORM_TRIPLET = x; then
15184-
LIBPL='$(prefix)'"/lib/python${VERSION}/config-${LDVERSION}"
15213+
LIBPL='$(prefix)'"/${platsubdir}/python${VERSION}/config-${LDVERSION}"
1518515214
else
15186-
LIBPL='$(prefix)'"/lib/python${VERSION}/config-${LDVERSION}-${PLATFORM_TRIPLET}"
15215+
LIBPL='$(prefix)'"/${platsubdir}/python${VERSION}/config-${LDVERSION}-${PLATFORM_TRIPLET}"
1518715216
fi
1518815217

1518915218

configure.ac

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4652,12 +4652,26 @@ else
46524652
LIBPYTHON=''
46534653
fi
46544654

4655+
# platsubdir must be defined before LIBPL definition
4656+
AC_MSG_CHECKING(for custom platsubdir)
4657+
AC_ARG_WITH(custom-platsubdir,
4658+
[AS_HELP_STRING([--with-custom-platsubdir=<libdirname>],
4659+
[name of the platform-specific lib subdirectory of $prefix. This is usually "lib", "lib32" or "lib64". Defaults to basename($libdir)])],
4660+
[],
4661+
[with_custom_platsubdir=yes])
4662+
AS_CASE($with_custom_platsubdir,
4663+
[yes],[platsubdir=`basename ${libdir}`],
4664+
[no],[platsubdir=lib],
4665+
[platsubdir=$with_custom_platsubdir])
4666+
AC_MSG_RESULT($platsubdir)
4667+
AC_SUBST(platsubdir)
4668+
46554669
dnl define LIBPL after ABIFLAGS and LDVERSION is defined.
46564670
AC_SUBST(PY_ENABLE_SHARED)
46574671
if test x$PLATFORM_TRIPLET = x; then
4658-
LIBPL='$(prefix)'"/lib/python${VERSION}/config-${LDVERSION}"
4672+
LIBPL='$(prefix)'"/${platsubdir}/python${VERSION}/config-${LDVERSION}"
46594673
else
4660-
LIBPL='$(prefix)'"/lib/python${VERSION}/config-${LDVERSION}-${PLATFORM_TRIPLET}"
4674+
LIBPL='$(prefix)'"/${platsubdir}/python${VERSION}/config-${LDVERSION}-${PLATFORM_TRIPLET}"
46614675
fi
46624676
AC_SUBST(LIBPL)
46634677

0 commit comments

Comments
 (0)