1 |
Signed-off-by: Michał Górny <mgorny@g.o> |
2 |
--- |
3 |
eclass/distutils-r2.eclass | 1198 ++++++++++++++++++++++++ |
4 |
eclass/python-any-r2.eclass | 357 ++++++++ |
5 |
eclass/python-r2.eclass | 825 +++++++++++++++++ |
6 |
eclass/python-single-r2.eclass | 507 +++++++++++ |
7 |
eclass/python-utils-r2.eclass | 1518 +++++++++++++++++++++++++++++++ |
8 |
eclass/tests/distutils-r2.sh | 98 ++ |
9 |
eclass/tests/python-utils-r2.sh | 237 +++++ |
10 |
7 files changed, 4740 insertions(+) |
11 |
create mode 100644 eclass/distutils-r2.eclass |
12 |
create mode 100644 eclass/python-any-r2.eclass |
13 |
create mode 100644 eclass/python-r2.eclass |
14 |
create mode 100644 eclass/python-single-r2.eclass |
15 |
create mode 100644 eclass/python-utils-r2.eclass |
16 |
create mode 100755 eclass/tests/distutils-r2.sh |
17 |
create mode 100755 eclass/tests/python-utils-r2.sh |
18 |
|
19 |
diff --git a/eclass/distutils-r2.eclass b/eclass/distutils-r2.eclass |
20 |
new file mode 100644 |
21 |
index 000000000000..662bad3b9bcd |
22 |
--- /dev/null |
23 |
+++ b/eclass/distutils-r2.eclass |
24 |
@@ -0,0 +1,1198 @@ |
25 |
+# Copyright 1999-2020 Gentoo Authors |
26 |
+# Distributed under the terms of the GNU General Public License v2 |
27 |
+ |
28 |
+# @ECLASS: distutils-r2.eclass |
29 |
+# @MAINTAINER: |
30 |
+# Python team <python@g.o> |
31 |
+# @AUTHOR: |
32 |
+# Author: Michał Górny <mgorny@g.o> |
33 |
+# @SUPPORTED_EAPIS: 5 6 7 |
34 |
+# @BLURB: A simple eclass to build Python packages using distutils. |
35 |
+# @DESCRIPTION: |
36 |
+# A simple eclass providing functions to build Python packages using |
37 |
+# the distutils build system. It exports phase functions for all |
38 |
+# the src_* phases. Each of the phases runs two pseudo-phases: |
39 |
+# python_..._all() (e.g. python_prepare_all()) once in ${S}, then |
40 |
+# python_...() (e.g. python_prepare()) for each implementation |
41 |
+# (see: python_foreach_impl() in python-r2). |
42 |
+# |
43 |
+# In distutils-r2_src_prepare(), the 'all' function is run before |
44 |
+# per-implementation ones (because it creates the implementations), |
45 |
+# per-implementation functions are run in a random order. |
46 |
+# |
47 |
+# In remaining phase functions, the per-implementation functions are run |
48 |
+# before the 'all' one, and they are ordered from the least to the most |
49 |
+# preferred implementation (so that 'better' files overwrite 'worse' |
50 |
+# ones). |
51 |
+# |
52 |
+# If the ebuild doesn't specify a particular pseudo-phase function, |
53 |
+# the default one will be used (distutils-r2_...). Defaults are provided |
54 |
+# for all per-implementation pseudo-phases, python_prepare_all() |
55 |
+# and python_install_all(); whenever writing your own pseudo-phase |
56 |
+# functions, you should consider calling the defaults (and especially |
57 |
+# distutils-r2_python_prepare_all). |
58 |
+# |
59 |
+# Please note that distutils-r2 sets RDEPEND and DEPEND unconditionally |
60 |
+# for you. |
61 |
+# |
62 |
+# Also, please note that distutils-r2 will always inherit python-r2 |
63 |
+# as well. Thus, all the variables defined and documented there are |
64 |
+# relevant to the packages using distutils-r2. |
65 |
+ |
66 |
+case "${EAPI:-0}" in |
67 |
+ 0|1|2|3|4) |
68 |
+ die "Unsupported EAPI=${EAPI:-0} (too old) for ${ECLASS}" |
69 |
+ ;; |
70 |
+ 5|6|7) |
71 |
+ ;; |
72 |
+ *) |
73 |
+ die "Unsupported EAPI=${EAPI} (unknown) for ${ECLASS}" |
74 |
+ ;; |
75 |
+esac |
76 |
+ |
77 |
+# @ECLASS-VARIABLE: DISTUTILS_OPTIONAL |
78 |
+# @DEFAULT_UNSET |
79 |
+# @DESCRIPTION: |
80 |
+# If set to a non-null value, distutils part in the ebuild will |
81 |
+# be considered optional. No dependencies will be added and no phase |
82 |
+# functions will be exported. |
83 |
+# |
84 |
+# If you enable DISTUTILS_OPTIONAL, you have to set proper dependencies |
85 |
+# for your package (using ${PYTHON_DEPS}) and to either call |
86 |
+# distutils-r2 default phase functions or call the build system |
87 |
+# manually. |
88 |
+ |
89 |
+# @ECLASS-VARIABLE: DISTUTILS_SINGLE_IMPL |
90 |
+# @DEFAULT_UNSET |
91 |
+# @DESCRIPTION: |
92 |
+# If set to a non-null value, the ebuild will support setting a single |
93 |
+# Python implementation only. It will effectively replace the python-r2 |
94 |
+# eclass inherit with python-single-r2. |
95 |
+# |
96 |
+# Note that inheriting python-single-r2 will cause pkg_setup() |
97 |
+# to be exported. It must be run in order for the eclass functions |
98 |
+# to function properly. |
99 |
+ |
100 |
+# @ECLASS-VARIABLE: DISTUTILS_USE_SETUPTOOLS |
101 |
+# @PRE_INHERIT |
102 |
+# @DESCRIPTION: |
103 |
+# Controls adding dev-python/setuptools dependency. The allowed values |
104 |
+# are: |
105 |
+# |
106 |
+# - no -- do not add the dependency (pure distutils package) |
107 |
+# - bdepend -- add it to BDEPEND (the default) |
108 |
+# - rdepend -- add it to BDEPEND+RDEPEND (when using entry_points) |
109 |
+# - pyproject.toml -- use pyproject2setuptools to install a project |
110 |
+# using pyproject.toml (flit, poetry...) |
111 |
+# - manual -- do not add the depedency and suppress the checks |
112 |
+# (assumes you will take care of doing it correctly) |
113 |
+# |
114 |
+# This variable is effective only if DISTUTILS_OPTIONAL is disabled. |
115 |
+# It needs to be set before the inherit line. |
116 |
+: ${DISTUTILS_USE_SETUPTOOLS:=bdepend} |
117 |
+ |
118 |
+if [[ ! ${_DISTUTILS_R2} ]]; then |
119 |
+ |
120 |
+[[ ${EAPI} == [456] ]] && inherit eutils |
121 |
+[[ ${EAPI} == [56] ]] && inherit xdg-utils |
122 |
+inherit multiprocessing toolchain-funcs |
123 |
+ |
124 |
+if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
125 |
+ inherit python-r2 |
126 |
+else |
127 |
+ inherit python-single-r2 |
128 |
+fi |
129 |
+ |
130 |
+fi |
131 |
+ |
132 |
+if [[ ! ${DISTUTILS_OPTIONAL} ]]; then |
133 |
+ EXPORT_FUNCTIONS src_prepare src_configure src_compile src_test src_install |
134 |
+fi |
135 |
+ |
136 |
+if [[ ! ${_DISTUTILS_R2} ]]; then |
137 |
+ |
138 |
+_distutils_set_globals() { |
139 |
+ local rdep=${PYTHON_DEPS} |
140 |
+ local bdep=${rdep} |
141 |
+ |
142 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
143 |
+ local sdep="dev-python/setuptools[${PYTHON_USEDEP}]" |
144 |
+ else |
145 |
+ local sdep="$(python_gen_cond_dep ' |
146 |
+ dev-python/setuptools[${PYTHON_MULTI_USEDEP}] |
147 |
+ ')" |
148 |
+ fi |
149 |
+ |
150 |
+ case ${DISTUTILS_USE_SETUPTOOLS} in |
151 |
+ no|manual) |
152 |
+ ;; |
153 |
+ bdepend) |
154 |
+ bdep+=" ${sdep}" |
155 |
+ ;; |
156 |
+ rdepend) |
157 |
+ bdep+=" ${sdep}" |
158 |
+ rdep+=" ${sdep}" |
159 |
+ ;; |
160 |
+ pyproject.toml) |
161 |
+ bdep+=" dev-python/pyproject2setuppy[${PYTHON_USEDEP}]" |
162 |
+ ;; |
163 |
+ *) |
164 |
+ die "Invalid DISTUTILS_USE_SETUPTOOLS=${DISTUTILS_USE_SETUPTOOLS}" |
165 |
+ ;; |
166 |
+ esac |
167 |
+ |
168 |
+ RDEPEND=${rdep} |
169 |
+ if [[ ${EAPI} != [56] ]]; then |
170 |
+ BDEPEND=${bdep} |
171 |
+ else |
172 |
+ DEPEND=${bdep} |
173 |
+ fi |
174 |
+ REQUIRED_USE=${PYTHON_REQUIRED_USE} |
175 |
+} |
176 |
+[[ ! ${DISTUTILS_OPTIONAL} ]] && _distutils_set_globals |
177 |
+unset -f _distutils_set_globals |
178 |
+ |
179 |
+# @ECLASS-VARIABLE: PATCHES |
180 |
+# @DEFAULT_UNSET |
181 |
+# @DESCRIPTION: |
182 |
+# An array containing patches to be applied to the sources before |
183 |
+# copying them. |
184 |
+# |
185 |
+# If unset, no custom patches will be applied. |
186 |
+# |
187 |
+# Please note, however, that at some point the eclass may apply |
188 |
+# additional distutils patches/quirks independently of this variable. |
189 |
+# |
190 |
+# Example: |
191 |
+# @CODE |
192 |
+# PATCHES=( "${FILESDIR}"/${P}-make-gentoo-happy.patch ) |
193 |
+# @CODE |
194 |
+ |
195 |
+# @ECLASS-VARIABLE: DOCS |
196 |
+# @DEFAULT_UNSET |
197 |
+# @DESCRIPTION: |
198 |
+# An array containing documents installed using dodoc. The files listed |
199 |
+# there must exist in the directory from which |
200 |
+# distutils-r2_python_install_all() is run (${S} by default). |
201 |
+# |
202 |
+# If unset, the function will instead look up files matching default |
203 |
+# filename pattern list (from the Package Manager Specification), |
204 |
+# and install those found. |
205 |
+# |
206 |
+# Example: |
207 |
+# @CODE |
208 |
+# DOCS=( NEWS README ) |
209 |
+# @CODE |
210 |
+ |
211 |
+# @ECLASS-VARIABLE: HTML_DOCS |
212 |
+# @DEFAULT_UNSET |
213 |
+# @DESCRIPTION: |
214 |
+# An array containing documents installed using dohtml. The files |
215 |
+# and directories listed there must exist in the directory from which |
216 |
+# distutils-r2_python_install_all() is run (${S} by default). |
217 |
+# |
218 |
+# If unset, no HTML docs will be installed. |
219 |
+# |
220 |
+# Example: |
221 |
+# @CODE |
222 |
+# HTML_DOCS=( doc/html/. ) |
223 |
+# @CODE |
224 |
+ |
225 |
+# @ECLASS-VARIABLE: EXAMPLES |
226 |
+# @DEFAULT_UNSET |
227 |
+# @DESCRIPTION: |
228 |
+# OBSOLETE: this variable is deprecated and banned in EAPI 6 |
229 |
+# |
230 |
+# An array containing examples installed into 'examples' doc |
231 |
+# subdirectory. The files and directories listed there must exist |
232 |
+# in the directory from which distutils-r2_python_install_all() is run |
233 |
+# (${S} by default). |
234 |
+# |
235 |
+# The 'examples' subdirectory will be marked not to be compressed |
236 |
+# automatically. |
237 |
+# |
238 |
+# If unset, no examples will be installed. |
239 |
+# |
240 |
+# Example: |
241 |
+# @CODE |
242 |
+# EXAMPLES=( examples/. demos/. ) |
243 |
+# @CODE |
244 |
+ |
245 |
+# @ECLASS-VARIABLE: DISTUTILS_IN_SOURCE_BUILD |
246 |
+# @DEFAULT_UNSET |
247 |
+# @DESCRIPTION: |
248 |
+# If set to a non-null value, in-source builds will be enabled. |
249 |
+# If unset, the default is to use in-source builds when python_prepare() |
250 |
+# is declared, and out-of-source builds otherwise. |
251 |
+# |
252 |
+# If in-source builds are used, the eclass will create a copy of package |
253 |
+# sources for each Python implementation in python_prepare_all(), |
254 |
+# and work on that copy afterwards. |
255 |
+# |
256 |
+# If out-of-source builds are used, the eclass will instead work |
257 |
+# on the sources directly, prepending setup.py arguments with |
258 |
+# 'build --build-base ${BUILD_DIR}' to enforce keeping & using built |
259 |
+# files in the specific root. |
260 |
+ |
261 |
+# @ECLASS-VARIABLE: DISTUTILS_ALL_SUBPHASE_IMPLS |
262 |
+# @DEFAULT_UNSET |
263 |
+# @DESCRIPTION: |
264 |
+# An array of patterns specifying which implementations can be used |
265 |
+# for *_all() sub-phase functions. If undefined, defaults to '*' |
266 |
+# (allowing any implementation). If multiple values are specified, |
267 |
+# implementations matching any of the patterns will be accepted. |
268 |
+# |
269 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
270 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
271 |
+# appropriately all enabled Python 2/3 implementations (alike |
272 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
273 |
+# to prevent accidental shell filename expansion. |
274 |
+# |
275 |
+# If the restriction needs to apply conditionally to a USE flag, |
276 |
+# the variable should be set conditionally as well (e.g. in an early |
277 |
+# phase function or other convenient location). |
278 |
+# |
279 |
+# Please remember to add a matching || block to REQUIRED_USE, |
280 |
+# to ensure that at least one implementation matching the patterns will |
281 |
+# be enabled. |
282 |
+# |
283 |
+# Example: |
284 |
+# @CODE |
285 |
+# REQUIRED_USE="doc? ( || ( $(python_gen_useflags 'python2*') ) )" |
286 |
+# |
287 |
+# pkg_setup() { |
288 |
+# use doc && DISTUTILS_ALL_SUBPHASE_IMPLS=( 'python2*' ) |
289 |
+# } |
290 |
+# @CODE |
291 |
+ |
292 |
+# @ECLASS-VARIABLE: mydistutilsargs |
293 |
+# @DEFAULT_UNSET |
294 |
+# @DESCRIPTION: |
295 |
+# An array containing options to be passed to setup.py. |
296 |
+# |
297 |
+# Example: |
298 |
+# @CODE |
299 |
+# python_configure_all() { |
300 |
+# mydistutilsargs=( --enable-my-hidden-option ) |
301 |
+# } |
302 |
+# @CODE |
303 |
+ |
304 |
+# @FUNCTION: distutils_enable_sphinx |
305 |
+# @USAGE: <subdir> [--no-autodoc | <plugin-pkgs>...] |
306 |
+# @DESCRIPTION: |
307 |
+# Set up IUSE, BDEPEND, python_check_deps() and python_compile_all() for |
308 |
+# building HTML docs via dev-python/sphinx. python_compile_all() will |
309 |
+# append to HTML_DOCS if docs are enabled. |
310 |
+# |
311 |
+# This helper is meant for the most common case, that is a single Sphinx |
312 |
+# subdirectory with standard layout, building and installing HTML docs |
313 |
+# behind USE=doc. It assumes it's the only consumer of the three |
314 |
+# aforementioned functions. If you need to use a custom implemention, |
315 |
+# you can't use it. |
316 |
+# |
317 |
+# If your package uses additional Sphinx plugins, they should be passed |
318 |
+# (without PYTHON_USEDEP) as <plugin-pkgs>. The function will take care |
319 |
+# of setting appropriate any-of dep and python_check_deps(). |
320 |
+# |
321 |
+# If no plugin packages are specified, the eclass will still utilize |
322 |
+# any-r2 API to support autodoc (documenting source code). |
323 |
+# If the package uses neither autodoc nor additional plugins, you should |
324 |
+# pass --no-autodoc to disable this API and simplify the resulting code. |
325 |
+# |
326 |
+# This function must be called in global scope. Take care not to |
327 |
+# overwrite the variables set by it. If you need to extend |
328 |
+# python_compile_all(), you can call the original implementation |
329 |
+# as sphinx_compile_all. |
330 |
+distutils_enable_sphinx() { |
331 |
+ debug-print-function ${FUNCNAME} "${@}" |
332 |
+ [[ ${#} -ge 1 ]] || die "${FUNCNAME} takes at least one arg: <subdir>" |
333 |
+ |
334 |
+ _DISTUTILS_SPHINX_SUBDIR=${1} |
335 |
+ shift |
336 |
+ _DISTUTILS_SPHINX_PLUGINS=( "${@}" ) |
337 |
+ |
338 |
+ local deps autodoc=1 d |
339 |
+ for d; do |
340 |
+ if [[ ${d} == --no-autodoc ]]; then |
341 |
+ autodoc= |
342 |
+ else |
343 |
+ deps+=" |
344 |
+ ${d}[\${PYTHON_USEDEP}]" |
345 |
+ fi |
346 |
+ done |
347 |
+ |
348 |
+ if [[ ! ${autodoc} && -n ${deps} ]]; then |
349 |
+ die "${FUNCNAME}: do not pass --no-autodoc if external plugins are used" |
350 |
+ fi |
351 |
+ if [[ ${autodoc} ]]; then |
352 |
+ deps="$(python_gen_any_dep " |
353 |
+ dev-python/sphinx[\${PYTHON_USEDEP}] |
354 |
+ ${deps}")" |
355 |
+ |
356 |
+ python_check_deps() { |
357 |
+ use doc || return 0 |
358 |
+ local p |
359 |
+ for p in dev-python/sphinx "${_DISTUTILS_SPHINX_PLUGINS[@]}"; do |
360 |
+ has_version "${p}[${PYTHON_USEDEP}]" || return 1 |
361 |
+ done |
362 |
+ } |
363 |
+ else |
364 |
+ deps="dev-python/sphinx" |
365 |
+ fi |
366 |
+ |
367 |
+ sphinx_compile_all() { |
368 |
+ use doc || return |
369 |
+ |
370 |
+ local confpy=${_DISTUTILS_SPHINX_SUBDIR}/conf.py |
371 |
+ [[ -f ${confpy} ]] || |
372 |
+ die "${confpy} not found, distutils_enable_sphinx call wrong" |
373 |
+ |
374 |
+ if [[ ${_DISTUTILS_SPHINX_PLUGINS[0]} == --no-autodoc ]]; then |
375 |
+ if grep -F -q 'sphinx.ext.autodoc' "${confpy}"; then |
376 |
+ die "distutils_enable_sphinx: --no-autodoc passed but sphinx.ext.autodoc found in ${confpy}" |
377 |
+ fi |
378 |
+ else |
379 |
+ if ! grep -F -q 'sphinx.ext.autodoc' "${confpy}"; then |
380 |
+ die "distutils_enable_sphinx: sphinx.ext.autodoc not found in ${confpy}, pass --no-autodoc" |
381 |
+ fi |
382 |
+ fi |
383 |
+ |
384 |
+ build_sphinx "${_DISTUTILS_SPHINX_SUBDIR}" |
385 |
+ } |
386 |
+ python_compile_all() { sphinx_compile_all; } |
387 |
+ |
388 |
+ IUSE+=" doc" |
389 |
+ if [[ ${EAPI} == [56] ]]; then |
390 |
+ DEPEND+=" doc? ( ${deps} )" |
391 |
+ else |
392 |
+ BDEPEND+=" doc? ( ${deps} )" |
393 |
+ fi |
394 |
+ |
395 |
+ # we need to ensure successful return in case we're called last, |
396 |
+ # otherwise Portage may wrongly assume sourcing failed |
397 |
+ return 0 |
398 |
+} |
399 |
+ |
400 |
+# @FUNCTION: distutils_enable_tests |
401 |
+# @USAGE: <test-runner> |
402 |
+# @DESCRIPTION: |
403 |
+# Set up IUSE, RESTRICT, BDEPEND and python_test() for running tests |
404 |
+# with the specified test runner. Also copies the current value |
405 |
+# of RDEPEND to test?-BDEPEND. The test-runner argument must be one of: |
406 |
+# |
407 |
+# - nose: nosetests (dev-python/nose) |
408 |
+# - pytest: dev-python/pytest |
409 |
+# - setup.py: setup.py test (no deps included) |
410 |
+# - unittest: for built-in Python unittest module |
411 |
+# |
412 |
+# This function is meant as a helper for common use cases, and it only |
413 |
+# takes care of basic setup. You still need to list additional test |
414 |
+# dependencies manually. If you have uncommon use case, you should |
415 |
+# not use it and instead enable tests manually. |
416 |
+# |
417 |
+# This function must be called in global scope, after RDEPEND has been |
418 |
+# declared. Take care not to overwrite the variables set by it. |
419 |
+distutils_enable_tests() { |
420 |
+ debug-print-function ${FUNCNAME} "${@}" |
421 |
+ [[ ${#} -eq 1 ]] || die "${FUNCNAME} takes exactly one argument: test-runner" |
422 |
+ |
423 |
+ local test_pkg |
424 |
+ case ${1} in |
425 |
+ nose) |
426 |
+ test_pkg="dev-python/nose" |
427 |
+ python_test() { |
428 |
+ nosetests -v || die "Tests fail with ${EPYTHON}" |
429 |
+ } |
430 |
+ ;; |
431 |
+ pytest) |
432 |
+ test_pkg="dev-python/pytest" |
433 |
+ python_test() { |
434 |
+ pytest -vv || die "Tests fail with ${EPYTHON}" |
435 |
+ } |
436 |
+ ;; |
437 |
+ setup.py) |
438 |
+ python_test() { |
439 |
+ esetup.py test --verbose |
440 |
+ } |
441 |
+ ;; |
442 |
+ unittest) |
443 |
+ python_test() { |
444 |
+ "${EPYTHON}" -m unittest discover -v || |
445 |
+ die "Tests fail with ${EPYTHON}" |
446 |
+ } |
447 |
+ ;; |
448 |
+ *) |
449 |
+ die "${FUNCNAME}: unsupported argument: ${1}" |
450 |
+ esac |
451 |
+ |
452 |
+ local test_deps=${RDEPEND} |
453 |
+ if [[ -n ${test_pkg} ]]; then |
454 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
455 |
+ test_deps+=" ${test_pkg}[${PYTHON_USEDEP}]" |
456 |
+ else |
457 |
+ test_deps+=" $(python_gen_cond_dep " |
458 |
+ ${test_pkg}[\${PYTHON_MULTI_USEDEP}] |
459 |
+ ")" |
460 |
+ fi |
461 |
+ fi |
462 |
+ if [[ -n ${test_deps} ]]; then |
463 |
+ IUSE+=" test" |
464 |
+ RESTRICT+=" !test? ( test )" |
465 |
+ if [[ ${EAPI} == [56] ]]; then |
466 |
+ DEPEND+=" test? ( ${test_deps} )" |
467 |
+ else |
468 |
+ BDEPEND+=" test? ( ${test_deps} )" |
469 |
+ fi |
470 |
+ fi |
471 |
+ |
472 |
+ # we need to ensure successful return in case we're called last, |
473 |
+ # otherwise Portage may wrongly assume sourcing failed |
474 |
+ return 0 |
475 |
+} |
476 |
+ |
477 |
+# @FUNCTION: _distutils-r2_verify_use_setuptools |
478 |
+# @INTERNAL |
479 |
+# @DESCRIPTION: |
480 |
+# Check setup.py for signs that DISTUTILS_USE_SETUPTOOLS have been set |
481 |
+# incorrectly. |
482 |
+_distutils_verify_use_setuptools() { |
483 |
+ [[ ${DISTUTILS_OPTIONAL} ]] && return |
484 |
+ [[ ${DISTUTILS_USE_SETUPTOOLS} == manual ]] && return |
485 |
+ [[ ${DISTUTILS_USE_SETUPTOOLS} == pyproject.toml ]] && return |
486 |
+ |
487 |
+ # ok, those are cheap greps. we can try toimprove them if we hit |
488 |
+ # false positives. |
489 |
+ local expected=no |
490 |
+ if [[ ${CATEGORY}/${PN} == dev-python/setuptools ]]; then |
491 |
+ # as a special case, setuptools provides itself ;-) |
492 |
+ : |
493 |
+ elif grep -E -q -s '(from|import)\s+setuptools' setup.py; then |
494 |
+ if grep -E -q -s 'entry_points\s*=' setup.py; then |
495 |
+ expected=rdepend |
496 |
+ elif grep -F -q -s '[options.entry_points]' setup.cfg; then |
497 |
+ expected=rdepend |
498 |
+ else |
499 |
+ expected=bdepend |
500 |
+ fi |
501 |
+ fi |
502 |
+ |
503 |
+ if [[ ${DISTUTILS_USE_SETUPTOOLS} != ${expected} ]]; then |
504 |
+ if [[ ! ${_DISTUTILS_SETUPTOOLS_WARNED} ]]; then |
505 |
+ _DISTUTILS_SETUPTOOLS_WARNED=1 |
506 |
+ local def= |
507 |
+ [[ ${DISTUTILS_USE_SETUPTOOLS} == bdepend ]] && def=' (default?)' |
508 |
+ |
509 |
+ eqawarn "DISTUTILS_USE_SETUPTOOLS value is probably incorrect" |
510 |
+ eqawarn " value: DISTUTILS_USE_SETUPTOOLS=${DISTUTILS_USE_SETUPTOOLS}${def}" |
511 |
+ eqawarn " expected: DISTUTILS_USE_SETUPTOOLS=${expected}" |
512 |
+ fi |
513 |
+ fi |
514 |
+} |
515 |
+ |
516 |
+# @FUNCTION: esetup.py |
517 |
+# @USAGE: [<args>...] |
518 |
+# @DESCRIPTION: |
519 |
+# Run setup.py using currently selected Python interpreter |
520 |
+# (if ${EPYTHON} is set; fallback 'python' otherwise). |
521 |
+# |
522 |
+# setup.py will be passed the following, in order: |
523 |
+# 1. ${mydistutilsargs[@]} |
524 |
+# 2. additional arguments passed to the esetup.py function. |
525 |
+# |
526 |
+# Please note that setup.py will respect defaults (unless overridden |
527 |
+# via command-line options) from setup.cfg that is created |
528 |
+# in distutils-r2_python_compile and in distutils-r2_python_install. |
529 |
+# |
530 |
+# This command dies on failure. |
531 |
+esetup.py() { |
532 |
+ debug-print-function ${FUNCNAME} "${@}" |
533 |
+ |
534 |
+ local die_args=() |
535 |
+ [[ ${EAPI} != [45] ]] && die_args+=( -n ) |
536 |
+ |
537 |
+ [[ ${BUILD_DIR} ]] && _distutils-r2_create_setup_cfg |
538 |
+ _distutils_verify_use_setuptools |
539 |
+ |
540 |
+ set -- "${EPYTHON:-python}" setup.py "${mydistutilsargs[@]}" "${@}" |
541 |
+ |
542 |
+ echo "${@}" >&2 |
543 |
+ "${@}" || die "${die_args[@]}" |
544 |
+ local ret=${?} |
545 |
+ |
546 |
+ if [[ ${BUILD_DIR} ]]; then |
547 |
+ rm "${HOME}"/.pydistutils.cfg || die "${die_args[@]}" |
548 |
+ fi |
549 |
+ |
550 |
+ return ${ret} |
551 |
+} |
552 |
+ |
553 |
+# @FUNCTION: distutils_install_for_testing |
554 |
+# @USAGE: [<args>...] |
555 |
+# @DESCRIPTION: |
556 |
+# Install the package into a temporary location for running tests. |
557 |
+# Update PYTHONPATH appropriately and set TEST_DIR to the test |
558 |
+# installation root. The Python packages will be installed in 'lib' |
559 |
+# subdir, and scripts in 'scripts' subdir (like in BUILD_DIR). |
560 |
+# |
561 |
+# Please note that this function should be only used if package uses |
562 |
+# namespaces (and therefore proper install needs to be done to enforce |
563 |
+# PYTHONPATH) or tests rely on the results of install command. |
564 |
+# For most of the packages, tests built in BUILD_DIR are good enough. |
565 |
+distutils_install_for_testing() { |
566 |
+ debug-print-function ${FUNCNAME} "${@}" |
567 |
+ |
568 |
+ # A few notes: |
569 |
+ # 1) because of namespaces, we can't use 'install --root', |
570 |
+ # 2) 'install --home' is terribly broken on pypy, so we need |
571 |
+ # to override --install-lib and --install-scripts, |
572 |
+ # 3) non-root 'install' complains about PYTHONPATH and missing dirs, |
573 |
+ # so we need to set it properly and mkdir them, |
574 |
+ # 4) it runs a bunch of commands which write random files to cwd, |
575 |
+ # in order to avoid that, we add the necessary path overrides |
576 |
+ # in _distutils-r2_create_setup_cfg. |
577 |
+ |
578 |
+ TEST_DIR=${BUILD_DIR}/test |
579 |
+ local bindir=${TEST_DIR}/scripts |
580 |
+ local libdir=${TEST_DIR}/lib |
581 |
+ PYTHONPATH=${libdir}:${PYTHONPATH} |
582 |
+ |
583 |
+ local add_args=( |
584 |
+ install |
585 |
+ --home="${TEST_DIR}" |
586 |
+ --install-lib="${libdir}" |
587 |
+ --install-scripts="${bindir}" |
588 |
+ ) |
589 |
+ |
590 |
+ mkdir -p "${libdir}" || die |
591 |
+ esetup.py "${add_args[@]}" "${@}" |
592 |
+} |
593 |
+ |
594 |
+# @FUNCTION: _distutils-r2_disable_ez_setup |
595 |
+# @INTERNAL |
596 |
+# @DESCRIPTION: |
597 |
+# Stub out ez_setup.py and distribute_setup.py to prevent packages |
598 |
+# from trying to download a local copy of setuptools. |
599 |
+_distutils-r2_disable_ez_setup() { |
600 |
+ local stub="def use_setuptools(*args, **kwargs): pass" |
601 |
+ if [[ -f ez_setup.py ]]; then |
602 |
+ echo "${stub}" > ez_setup.py || die |
603 |
+ fi |
604 |
+ if [[ -f distribute_setup.py ]]; then |
605 |
+ echo "${stub}" > distribute_setup.py || die |
606 |
+ fi |
607 |
+} |
608 |
+ |
609 |
+# @FUNCTION: _distutils-r2_handle_pyproject_toml |
610 |
+# @INTERNAL |
611 |
+# @DESCRIPTION: |
612 |
+# Generate setup.py for pyproject.toml if requested. |
613 |
+_distutils-r2_handle_pyproject_toml() { |
614 |
+ if [[ ! -f setup.py && -f pyproject.toml ]]; then |
615 |
+ if [[ ${DISTUTILS_USE_SETUPTOOLS} == pyproject.toml ]]; then |
616 |
+ cat > setup.py <<-EOF || die |
617 |
+ #!/usr/bin/env python |
618 |
+ from pyproject2setuppy.main import main |
619 |
+ main() |
620 |
+ EOF |
621 |
+ chmod +x setup.py || die |
622 |
+ else |
623 |
+ eerror "No setup.py found but pyproject.toml is present. In order to enable" |
624 |
+ eerror "pyproject.toml support in distutils-r2, set:" |
625 |
+ eerror " DISTUTILS_USE_SETUPTOOLS=pyproject.toml" |
626 |
+ die "No setup.py found and DISTUTILS_USE_SETUPTOOLS!=pyproject.toml" |
627 |
+ fi |
628 |
+ fi |
629 |
+} |
630 |
+ |
631 |
+# @FUNCTION: distutils-r2_python_prepare_all |
632 |
+# @DESCRIPTION: |
633 |
+# The default python_prepare_all(). It applies the patches from PATCHES |
634 |
+# array, then user patches and finally calls python_copy_sources to |
635 |
+# create copies of resulting sources for each Python implementation. |
636 |
+# |
637 |
+# At some point in the future, it may also apply eclass-specific |
638 |
+# distutils patches and/or quirks. |
639 |
+distutils-r2_python_prepare_all() { |
640 |
+ debug-print-function ${FUNCNAME} "${@}" |
641 |
+ |
642 |
+ if [[ ! ${DISTUTILS_OPTIONAL} ]]; then |
643 |
+ if [[ ${EAPI} != [45] ]]; then |
644 |
+ default |
645 |
+ else |
646 |
+ [[ ${PATCHES} ]] && epatch "${PATCHES[@]}" |
647 |
+ epatch_user |
648 |
+ fi |
649 |
+ fi |
650 |
+ |
651 |
+ # by default, use in-source build if python_prepare() is used |
652 |
+ if [[ ! ${DISTUTILS_IN_SOURCE_BUILD+1} ]]; then |
653 |
+ if declare -f python_prepare >/dev/null; then |
654 |
+ DISTUTILS_IN_SOURCE_BUILD=1 |
655 |
+ fi |
656 |
+ fi |
657 |
+ |
658 |
+ _distutils-r2_disable_ez_setup |
659 |
+ _distutils-r2_handle_pyproject_toml |
660 |
+ |
661 |
+ if [[ ${DISTUTILS_IN_SOURCE_BUILD} && ! ${DISTUTILS_SINGLE_IMPL} ]] |
662 |
+ then |
663 |
+ # create source copies for each implementation |
664 |
+ python_copy_sources |
665 |
+ fi |
666 |
+ |
667 |
+ _DISTUTILS_DEFAULT_CALLED=1 |
668 |
+} |
669 |
+ |
670 |
+# @FUNCTION: distutils-r2_python_prepare |
671 |
+# @DESCRIPTION: |
672 |
+# The default python_prepare(). A no-op. |
673 |
+distutils-r2_python_prepare() { |
674 |
+ debug-print-function ${FUNCNAME} "${@}" |
675 |
+ |
676 |
+ [[ ${EAPI} == [45] ]] || die "${FUNCNAME} is banned in EAPI 6 (it was a no-op)" |
677 |
+} |
678 |
+ |
679 |
+# @FUNCTION: distutils-r2_python_configure |
680 |
+# @DESCRIPTION: |
681 |
+# The default python_configure(). A no-op. |
682 |
+distutils-r2_python_configure() { |
683 |
+ debug-print-function ${FUNCNAME} "${@}" |
684 |
+ |
685 |
+ [[ ${EAPI} == [45] ]] || die "${FUNCNAME} is banned in EAPI 6 (it was a no-op)" |
686 |
+} |
687 |
+ |
688 |
+# @FUNCTION: _distutils-r2_create_setup_cfg |
689 |
+# @INTERNAL |
690 |
+# @DESCRIPTION: |
691 |
+# Create implementation-specific configuration file for distutils, |
692 |
+# setting proper build-dir (and install-dir) paths. |
693 |
+_distutils-r2_create_setup_cfg() { |
694 |
+ cat > "${HOME}"/.pydistutils.cfg <<-_EOF_ || die |
695 |
+ [build] |
696 |
+ build-base = ${BUILD_DIR} |
697 |
+ |
698 |
+ # using a single directory for them helps us export |
699 |
+ # ${PYTHONPATH} and ebuilds find the sources independently |
700 |
+ # of whether the package installs extensions or not |
701 |
+ # |
702 |
+ # note: due to some packages (wxpython) relying on separate |
703 |
+ # platlib & purelib dirs, we do not set --build-lib (which |
704 |
+ # can not be overridden with --build-*lib) |
705 |
+ build-platlib = %(build-base)s/lib |
706 |
+ build-purelib = %(build-base)s/lib |
707 |
+ |
708 |
+ # make the ebuild writer lives easier |
709 |
+ build-scripts = %(build-base)s/scripts |
710 |
+ |
711 |
+ # this is needed by distutils_install_for_testing since |
712 |
+ # setuptools like to create .egg files for install --home. |
713 |
+ [bdist_egg] |
714 |
+ dist-dir = ${BUILD_DIR}/dist |
715 |
+ _EOF_ |
716 |
+ |
717 |
+ # we can't refer to ${D} before src_install() |
718 |
+ if [[ ${EBUILD_PHASE} == install ]]; then |
719 |
+ cat >> "${HOME}"/.pydistutils.cfg <<-_EOF_ || die |
720 |
+ |
721 |
+ # installation paths -- allow calling extra install targets |
722 |
+ # without the default 'install' |
723 |
+ [install] |
724 |
+ compile = True |
725 |
+ optimize = 2 |
726 |
+ root = ${D%/} |
727 |
+ _EOF_ |
728 |
+ |
729 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
730 |
+ cat >> "${HOME}"/.pydistutils.cfg <<-_EOF_ || die |
731 |
+ install-scripts = $(python_get_scriptdir) |
732 |
+ _EOF_ |
733 |
+ fi |
734 |
+ fi |
735 |
+} |
736 |
+ |
737 |
+# @FUNCTION: _distutils-r2_copy_egg_info |
738 |
+# @INTERNAL |
739 |
+# @DESCRIPTION: |
740 |
+# Copy egg-info files to the ${BUILD_DIR} (that's going to become |
741 |
+# egg-base in esetup.py). This way, we respect whatever's in upstream |
742 |
+# egg-info. |
743 |
+_distutils-r2_copy_egg_info() { |
744 |
+ mkdir -p "${BUILD_DIR}" || die |
745 |
+ # stupid freebsd can't do 'cp -t ${BUILD_DIR} {} +' |
746 |
+ find -name '*.egg-info' -type d -exec cp -R -p {} "${BUILD_DIR}"/ ';' || die |
747 |
+} |
748 |
+ |
749 |
+# @FUNCTION: distutils-r2_python_compile |
750 |
+# @USAGE: [additional-args...] |
751 |
+# @DESCRIPTION: |
752 |
+# The default python_compile(). Runs 'esetup.py build'. Any parameters |
753 |
+# passed to this function will be appended to setup.py invocation, |
754 |
+# i.e. passed as options to the 'build' command. |
755 |
+# |
756 |
+# This phase also sets up initial setup.cfg with build directories |
757 |
+# and copies upstream egg-info files if supplied. |
758 |
+distutils-r2_python_compile() { |
759 |
+ debug-print-function ${FUNCNAME} "${@}" |
760 |
+ |
761 |
+ _distutils-r2_copy_egg_info |
762 |
+ |
763 |
+ local build_args=() |
764 |
+ # distutils is parallel-capable since py3.5 |
765 |
+ # to avoid breaking stable ebuilds, enable it only if either: |
766 |
+ # a. we're dealing with EAPI 7 |
767 |
+ # b. we're dealing with Python 3.7 or PyPy3 |
768 |
+ if python_is_python3 && [[ ${EPYTHON} != python3.4 ]]; then |
769 |
+ if [[ ${EAPI} != [56] || ${EPYTHON} != python3.[56] ]]; then |
770 |
+ local jobs=$(makeopts_jobs "${MAKEOPTS}" INF) |
771 |
+ if [[ ${jobs} == INF ]]; then |
772 |
+ local nproc=$(get_nproc) |
773 |
+ jobs=$(( nproc + 1 )) |
774 |
+ fi |
775 |
+ build_args+=( -j "${jobs}" ) |
776 |
+ fi |
777 |
+ fi |
778 |
+ |
779 |
+ esetup.py build "${build_args[@]}" "${@}" |
780 |
+} |
781 |
+ |
782 |
+# @FUNCTION: _distutils-r2_wrap_scripts |
783 |
+# @USAGE: <path> <bindir> |
784 |
+# @INTERNAL |
785 |
+# @DESCRIPTION: |
786 |
+# Moves and wraps all installed scripts/executables as necessary. |
787 |
+_distutils-r2_wrap_scripts() { |
788 |
+ debug-print-function ${FUNCNAME} "${@}" |
789 |
+ |
790 |
+ [[ ${#} -eq 2 ]] || die "usage: ${FUNCNAME} <path> <bindir>" |
791 |
+ local path=${1} |
792 |
+ local bindir=${2} |
793 |
+ |
794 |
+ local PYTHON_SCRIPTDIR |
795 |
+ python_export PYTHON_SCRIPTDIR |
796 |
+ |
797 |
+ local f python_files=() non_python_files=() |
798 |
+ |
799 |
+ if [[ -d ${path}${PYTHON_SCRIPTDIR} ]]; then |
800 |
+ for f in "${path}${PYTHON_SCRIPTDIR}"/*; do |
801 |
+ [[ -d ${f} ]] && die "Unexpected directory: ${f}" |
802 |
+ debug-print "${FUNCNAME}: found executable at ${f#${path}/}" |
803 |
+ |
804 |
+ local shebang |
805 |
+ read -r shebang < "${f}" |
806 |
+ if [[ ${shebang} == '#!'*${EPYTHON}* ]]; then |
807 |
+ debug-print "${FUNCNAME}: matching shebang: ${shebang}" |
808 |
+ python_files+=( "${f}" ) |
809 |
+ else |
810 |
+ debug-print "${FUNCNAME}: non-matching shebang: ${shebang}" |
811 |
+ non_python_files+=( "${f}" ) |
812 |
+ fi |
813 |
+ |
814 |
+ mkdir -p "${path}${bindir}" || die |
815 |
+ done |
816 |
+ |
817 |
+ for f in "${python_files[@]}"; do |
818 |
+ local basename=${f##*/} |
819 |
+ |
820 |
+ debug-print "${FUNCNAME}: installing wrapper at ${bindir}/${basename}" |
821 |
+ _python_ln_rel "${path}${EPREFIX}"/usr/lib/python-exec/python-exec2 \ |
822 |
+ "${path}${bindir}/${basename}" || die |
823 |
+ done |
824 |
+ |
825 |
+ for f in "${non_python_files[@]}"; do |
826 |
+ local basename=${f##*/} |
827 |
+ |
828 |
+ debug-print "${FUNCNAME}: moving ${f#${path}/} to ${bindir}/${basename}" |
829 |
+ mv "${f}" "${path}${bindir}/${basename}" || die |
830 |
+ done |
831 |
+ fi |
832 |
+} |
833 |
+ |
834 |
+# @FUNCTION: distutils-r2_python_install |
835 |
+# @USAGE: [additional-args...] |
836 |
+# @DESCRIPTION: |
837 |
+# The default python_install(). Runs 'esetup.py install', doing |
838 |
+# intermediate root install and handling script wrapping afterwards. |
839 |
+# Any parameters passed to this function will be appended |
840 |
+# to the setup.py invocation (i.e. as options to the 'install' command). |
841 |
+# |
842 |
+# This phase updates the setup.cfg file with install directories. |
843 |
+distutils-r2_python_install() { |
844 |
+ debug-print-function ${FUNCNAME} "${@}" |
845 |
+ |
846 |
+ local args=( "${@}" ) |
847 |
+ |
848 |
+ # enable compilation for the install phase. |
849 |
+ local -x PYTHONDONTWRITEBYTECODE= |
850 |
+ |
851 |
+ # python likes to compile any module it sees, which triggers sandbox |
852 |
+ # failures if some packages haven't compiled their modules yet. |
853 |
+ addpredict "${EPREFIX}/usr/lib/${EPYTHON}" |
854 |
+ addpredict "${EPREFIX}/usr/$(get_libdir)/${EPYTHON}" |
855 |
+ addpredict /usr/lib/pypy2.7 |
856 |
+ addpredict /usr/lib/pypy3.6 |
857 |
+ addpredict /usr/lib/portage/pym |
858 |
+ addpredict /usr/local # bug 498232 |
859 |
+ |
860 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
861 |
+ # user may override --install-scripts |
862 |
+ # note: this is poor but distutils argv parsing is dumb |
863 |
+ local mydistutilsargs=( "${mydistutilsargs[@]}" ) |
864 |
+ local scriptdir=${EPREFIX}/usr/bin |
865 |
+ |
866 |
+ # construct a list of mydistutilsargs[0] args[0] args[1]... |
867 |
+ local arg arg_vars |
868 |
+ [[ ${mydistutilsargs[@]} ]] && eval arg_vars+=( |
869 |
+ 'mydistutilsargs['{0..$(( ${#mydistutilsargs[@]} - 1 ))}']' |
870 |
+ ) |
871 |
+ [[ ${args[@]} ]] && eval arg_vars+=( |
872 |
+ 'args['{0..$(( ${#args[@]} - 1 ))}']' |
873 |
+ ) |
874 |
+ |
875 |
+ set -- "${arg_vars[@]}" |
876 |
+ while [[ ${@} ]]; do |
877 |
+ local arg_var=${1} |
878 |
+ shift |
879 |
+ local a=${!arg_var} |
880 |
+ |
881 |
+ case "${a}" in |
882 |
+ --install-scripts=*) |
883 |
+ scriptdir=${a#--install-scripts=} |
884 |
+ unset "${arg_var}" |
885 |
+ ;; |
886 |
+ --install-scripts) |
887 |
+ scriptdir=${!1} |
888 |
+ unset "${arg_var}" "${1}" |
889 |
+ shift |
890 |
+ ;; |
891 |
+ esac |
892 |
+ done |
893 |
+ fi |
894 |
+ |
895 |
+ local root=${D%/}/_${EPYTHON} |
896 |
+ [[ ${DISTUTILS_SINGLE_IMPL} ]] && root=${D%/} |
897 |
+ |
898 |
+ esetup.py install --root="${root}" "${args[@]}" |
899 |
+ |
900 |
+ local forbidden_package_names=( examples test tests .pytest_cache ) |
901 |
+ local p |
902 |
+ for p in "${forbidden_package_names[@]}"; do |
903 |
+ if [[ -d ${root}$(python_get_sitedir)/${p} ]]; then |
904 |
+ die "Package installs '${p}' package which is forbidden and likely a bug in the build system." |
905 |
+ fi |
906 |
+ done |
907 |
+ |
908 |
+ local shopt_save=$(shopt -p nullglob) |
909 |
+ shopt -s nullglob |
910 |
+ local pypy_dirs=( |
911 |
+ "${root}/usr/$(get_libdir)"/pypy*/share |
912 |
+ "${root}/usr/lib"/pypy*/share |
913 |
+ ) |
914 |
+ ${shopt_save} |
915 |
+ |
916 |
+ if [[ -n ${pypy_dirs} ]]; then |
917 |
+ local cmd=die |
918 |
+ [[ ${EAPI} == [45] ]] && cmd=eqawarn |
919 |
+ "${cmd}" "Package installs 'share' in PyPy prefix, see bug #465546." |
920 |
+ fi |
921 |
+ |
922 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
923 |
+ _distutils-r2_wrap_scripts "${root}" "${scriptdir}" |
924 |
+ multibuild_merge_root "${root}" "${D%/}" |
925 |
+ fi |
926 |
+} |
927 |
+ |
928 |
+# @FUNCTION: distutils-r2_python_install_all |
929 |
+# @DESCRIPTION: |
930 |
+# The default python_install_all(). It installs the documentation. |
931 |
+distutils-r2_python_install_all() { |
932 |
+ debug-print-function ${FUNCNAME} "${@}" |
933 |
+ |
934 |
+ einstalldocs |
935 |
+ |
936 |
+ if declare -p EXAMPLES &>/dev/null; then |
937 |
+ [[ ${EAPI} != [45] ]] && die "EXAMPLES are banned in EAPI ${EAPI}" |
938 |
+ |
939 |
+ ( |
940 |
+ docinto examples |
941 |
+ dodoc -r "${EXAMPLES[@]}" |
942 |
+ ) |
943 |
+ docompress -x "/usr/share/doc/${PF}/examples" |
944 |
+ fi |
945 |
+ |
946 |
+ _DISTUTILS_DEFAULT_CALLED=1 |
947 |
+} |
948 |
+ |
949 |
+# @FUNCTION: distutils-r2_run_phase |
950 |
+# @USAGE: [<argv>...] |
951 |
+# @INTERNAL |
952 |
+# @DESCRIPTION: |
953 |
+# Run the given command. |
954 |
+# |
955 |
+# If out-of-source builds are used, the phase function is run in source |
956 |
+# directory, with BUILD_DIR pointing at the build directory |
957 |
+# and PYTHONPATH having an entry for the module build directory. |
958 |
+# |
959 |
+# If in-source builds are used, the command is executed in the directory |
960 |
+# holding the per-implementation copy of sources. BUILD_DIR points |
961 |
+# to the 'build' subdirectory. |
962 |
+distutils-r2_run_phase() { |
963 |
+ debug-print-function ${FUNCNAME} "${@}" |
964 |
+ |
965 |
+ if [[ ${DISTUTILS_IN_SOURCE_BUILD} ]]; then |
966 |
+ # only force BUILD_DIR if implementation is explicitly enabled |
967 |
+ # for building; any-r2 API may select one that is not |
968 |
+ # https://bugs.gentoo.org/701506 |
969 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]] && |
970 |
+ has "${EPYTHON/./_}" ${PYTHON_TARGETS}; then |
971 |
+ cd "${BUILD_DIR}" || die |
972 |
+ fi |
973 |
+ local BUILD_DIR=${BUILD_DIR}/build |
974 |
+ fi |
975 |
+ local -x PYTHONPATH="${BUILD_DIR}/lib:${PYTHONPATH}" |
976 |
+ |
977 |
+ # Bug 559644 |
978 |
+ # using PYTHONPATH when the ${BUILD_DIR}/lib is not created yet might lead to |
979 |
+ # problems in setup.py scripts that try to import modules/packages from that path |
980 |
+ # during the build process (Python at startup evaluates PYTHONPATH, if the dir is |
981 |
+ # not valid then associates a NullImporter object to ${BUILD_DIR}/lib storing it |
982 |
+ # in the sys.path_importer_cache) |
983 |
+ mkdir -p "${BUILD_DIR}/lib" || die |
984 |
+ |
985 |
+ # Set up build environment, bug #513664. |
986 |
+ local -x AR=${AR} CC=${CC} CPP=${CPP} CXX=${CXX} |
987 |
+ tc-export AR CC CPP CXX |
988 |
+ |
989 |
+ # How to build Python modules in different worlds... |
990 |
+ local ldopts |
991 |
+ case "${CHOST}" in |
992 |
+ # provided by haubi, 2014-07-08 |
993 |
+ *-aix*) ldopts='-shared -Wl,-berok';; # good enough |
994 |
+ # provided by grobian, 2014-06-22, bug #513664 c7 |
995 |
+ *-darwin*) ldopts='-bundle -undefined dynamic_lookup';; |
996 |
+ *) ldopts='-shared';; |
997 |
+ esac |
998 |
+ |
999 |
+ local -x LDSHARED="${CC} ${ldopts}" LDCXXSHARED="${CXX} ${ldopts}" |
1000 |
+ |
1001 |
+ "${@}" |
1002 |
+ |
1003 |
+ cd "${_DISTUTILS_INITIAL_CWD}" || die |
1004 |
+} |
1005 |
+ |
1006 |
+# @FUNCTION: _distutils-r2_run_common_phase |
1007 |
+# @USAGE: [<argv>...] |
1008 |
+# @INTERNAL |
1009 |
+# @DESCRIPTION: |
1010 |
+# Run the given command, restoring the state for a most preferred Python |
1011 |
+# implementation matching DISTUTILS_ALL_SUBPHASE_IMPLS. |
1012 |
+# |
1013 |
+# If in-source build is used, the command will be run in the copy |
1014 |
+# of sources made for the selected Python interpreter. |
1015 |
+_distutils-r2_run_common_phase() { |
1016 |
+ local DISTUTILS_ORIG_BUILD_DIR=${BUILD_DIR} |
1017 |
+ |
1018 |
+ if [[ ${DISTUTILS_SINGLE_IMPL} ]]; then |
1019 |
+ # reuse the dedicated code branch |
1020 |
+ _distutils-r2_run_foreach_impl "${@}" |
1021 |
+ else |
1022 |
+ local -x EPYTHON PYTHON |
1023 |
+ local -x PATH=${PATH} PKG_CONFIG_PATH=${PKG_CONFIG_PATH} |
1024 |
+ python_setup "${DISTUTILS_ALL_SUBPHASE_IMPLS[@]}" |
1025 |
+ |
1026 |
+ local MULTIBUILD_VARIANTS=( "${EPYTHON/./_}" ) |
1027 |
+ # store for restoring after distutils-r2_run_phase. |
1028 |
+ local _DISTUTILS_INITIAL_CWD=${PWD} |
1029 |
+ multibuild_foreach_variant \ |
1030 |
+ distutils-r2_run_phase "${@}" |
1031 |
+ fi |
1032 |
+} |
1033 |
+ |
1034 |
+# @FUNCTION: _distutils-r2_run_foreach_impl |
1035 |
+# @INTERNAL |
1036 |
+# @DESCRIPTION: |
1037 |
+# Run the given phase for each implementation if multiple implementations |
1038 |
+# are enabled, once otherwise. |
1039 |
+_distutils-r2_run_foreach_impl() { |
1040 |
+ debug-print-function ${FUNCNAME} "${@}" |
1041 |
+ |
1042 |
+ # store for restoring after distutils-r2_run_phase. |
1043 |
+ local _DISTUTILS_INITIAL_CWD=${PWD} |
1044 |
+ set -- distutils-r2_run_phase "${@}" |
1045 |
+ |
1046 |
+ if [[ ! ${DISTUTILS_SINGLE_IMPL} ]]; then |
1047 |
+ python_foreach_impl "${@}" |
1048 |
+ else |
1049 |
+ if [[ ! ${EPYTHON} ]]; then |
1050 |
+ die "EPYTHON unset, python-single-r2_pkg_setup not called?!" |
1051 |
+ fi |
1052 |
+ local BUILD_DIR=${BUILD_DIR:-${S}} |
1053 |
+ BUILD_DIR=${BUILD_DIR%%/}_${EPYTHON} |
1054 |
+ |
1055 |
+ "${@}" |
1056 |
+ fi |
1057 |
+} |
1058 |
+ |
1059 |
+distutils-r2_src_prepare() { |
1060 |
+ debug-print-function ${FUNCNAME} "${@}" |
1061 |
+ |
1062 |
+ local _DISTUTILS_DEFAULT_CALLED |
1063 |
+ |
1064 |
+ # common preparations |
1065 |
+ if declare -f python_prepare_all >/dev/null; then |
1066 |
+ python_prepare_all |
1067 |
+ else |
1068 |
+ distutils-r2_python_prepare_all |
1069 |
+ fi |
1070 |
+ |
1071 |
+ if [[ ! ${_DISTUTILS_DEFAULT_CALLED} ]]; then |
1072 |
+ local cmd=die |
1073 |
+ [[ ${EAPI} == [45] ]] && cmd=eqawarn |
1074 |
+ |
1075 |
+ "${cmd}" "QA: python_prepare_all() didn't call distutils-r2_python_prepare_all" |
1076 |
+ fi |
1077 |
+ |
1078 |
+ if declare -f python_prepare >/dev/null; then |
1079 |
+ _distutils-r2_run_foreach_impl python_prepare |
1080 |
+ fi |
1081 |
+} |
1082 |
+ |
1083 |
+distutils-r2_src_configure() { |
1084 |
+ python_export_utf8_locale |
1085 |
+ [[ ${EAPI} == [56] ]] && xdg_environment_reset # Bug 577704 |
1086 |
+ |
1087 |
+ if declare -f python_configure >/dev/null; then |
1088 |
+ _distutils-r2_run_foreach_impl python_configure |
1089 |
+ fi |
1090 |
+ |
1091 |
+ if declare -f python_configure_all >/dev/null; then |
1092 |
+ _distutils-r2_run_common_phase python_configure_all |
1093 |
+ fi |
1094 |
+} |
1095 |
+ |
1096 |
+distutils-r2_src_compile() { |
1097 |
+ debug-print-function ${FUNCNAME} "${@}" |
1098 |
+ |
1099 |
+ if declare -f python_compile >/dev/null; then |
1100 |
+ _distutils-r2_run_foreach_impl python_compile |
1101 |
+ else |
1102 |
+ _distutils-r2_run_foreach_impl distutils-r2_python_compile |
1103 |
+ fi |
1104 |
+ |
1105 |
+ if declare -f python_compile_all >/dev/null; then |
1106 |
+ _distutils-r2_run_common_phase python_compile_all |
1107 |
+ fi |
1108 |
+} |
1109 |
+ |
1110 |
+# @FUNCTION: _distutils-r2_clean_egg_info |
1111 |
+# @INTERNAL |
1112 |
+# @DESCRIPTION: |
1113 |
+# Clean up potential stray egg-info files left by setuptools test phase. |
1114 |
+# Those files ended up being unversioned, and caused issues: |
1115 |
+# https://bugs.gentoo.org/534058 |
1116 |
+_distutils-r2_clean_egg_info() { |
1117 |
+ rm -rf "${BUILD_DIR}"/lib/*.egg-info || die |
1118 |
+} |
1119 |
+ |
1120 |
+distutils-r2_src_test() { |
1121 |
+ debug-print-function ${FUNCNAME} "${@}" |
1122 |
+ |
1123 |
+ if declare -f python_test >/dev/null; then |
1124 |
+ _distutils-r2_run_foreach_impl python_test |
1125 |
+ _distutils-r2_run_foreach_impl _distutils-r2_clean_egg_info |
1126 |
+ fi |
1127 |
+ |
1128 |
+ if declare -f python_test_all >/dev/null; then |
1129 |
+ _distutils-r2_run_common_phase python_test_all |
1130 |
+ fi |
1131 |
+} |
1132 |
+ |
1133 |
+# @FUNCTION: _distutils-r2_check_namespace_pth |
1134 |
+# @INTERNAL |
1135 |
+# @DESCRIPTION: |
1136 |
+# Check if any *-nspkg.pth files were installed (by setuptools) |
1137 |
+# and warn about the policy non-conformance if they were. |
1138 |
+_distutils-r2_check_namespace_pth() { |
1139 |
+ local f pth=() |
1140 |
+ |
1141 |
+ while IFS= read -r -d '' f; do |
1142 |
+ pth+=( "${f}" ) |
1143 |
+ done < <(find "${ED%/}" -name '*-nspkg.pth' -print0) |
1144 |
+ |
1145 |
+ if [[ ${pth[@]} ]]; then |
1146 |
+ ewarn "The following *-nspkg.pth files were found installed:" |
1147 |
+ ewarn |
1148 |
+ for f in "${pth[@]}"; do |
1149 |
+ ewarn " ${f#${ED%/}}" |
1150 |
+ done |
1151 |
+ ewarn |
1152 |
+ ewarn "The presence of those files may break namespaces in Python 3.5+. Please" |
1153 |
+ ewarn "read our documentation on reliable handling of namespaces and update" |
1154 |
+ ewarn "the ebuild accordingly:" |
1155 |
+ ewarn |
1156 |
+ ewarn " https://wiki.gentoo.org/wiki/Project:Python/Namespace_packages" |
1157 |
+ fi |
1158 |
+} |
1159 |
+ |
1160 |
+distutils-r2_src_install() { |
1161 |
+ debug-print-function ${FUNCNAME} "${@}" |
1162 |
+ |
1163 |
+ if declare -f python_install >/dev/null; then |
1164 |
+ _distutils-r2_run_foreach_impl python_install |
1165 |
+ else |
1166 |
+ _distutils-r2_run_foreach_impl distutils-r2_python_install |
1167 |
+ fi |
1168 |
+ |
1169 |
+ local _DISTUTILS_DEFAULT_CALLED |
1170 |
+ |
1171 |
+ if declare -f python_install_all >/dev/null; then |
1172 |
+ _distutils-r2_run_common_phase python_install_all |
1173 |
+ else |
1174 |
+ _distutils-r2_run_common_phase distutils-r2_python_install_all |
1175 |
+ fi |
1176 |
+ |
1177 |
+ if [[ ! ${_DISTUTILS_DEFAULT_CALLED} ]]; then |
1178 |
+ local cmd=die |
1179 |
+ [[ ${EAPI} == [45] ]] && cmd=eqawarn |
1180 |
+ |
1181 |
+ "${cmd}" "QA: python_install_all() didn't call distutils-r2_python_install_all" |
1182 |
+ fi |
1183 |
+ |
1184 |
+ _distutils-r2_check_namespace_pth |
1185 |
+} |
1186 |
+ |
1187 |
+# -- distutils.eclass functions -- |
1188 |
+ |
1189 |
+distutils_get_intermediate_installation_image() { |
1190 |
+ die "${FUNCNAME}() is invalid for distutils-r2" |
1191 |
+} |
1192 |
+ |
1193 |
+distutils_src_unpack() { |
1194 |
+ die "${FUNCNAME}() is invalid for distutils-r2, and you don't want it in EAPI ${EAPI} anyway" |
1195 |
+} |
1196 |
+ |
1197 |
+distutils_src_prepare() { |
1198 |
+ die "${FUNCNAME}() is invalid for distutils-r2, you probably want: ${FUNCNAME/_/-r2_}" |
1199 |
+} |
1200 |
+ |
1201 |
+distutils_src_compile() { |
1202 |
+ die "${FUNCNAME}() is invalid for distutils-r2, you probably want: ${FUNCNAME/_/-r2_}" |
1203 |
+} |
1204 |
+ |
1205 |
+distutils_src_test() { |
1206 |
+ die "${FUNCNAME}() is invalid for distutils-r2, you probably want: ${FUNCNAME/_/-r2_}" |
1207 |
+} |
1208 |
+ |
1209 |
+distutils_src_install() { |
1210 |
+ die "${FUNCNAME}() is invalid for distutils-r2, you probably want: ${FUNCNAME/_/-r2_}" |
1211 |
+} |
1212 |
+ |
1213 |
+distutils_pkg_postinst() { |
1214 |
+ die "${FUNCNAME}() is invalid for distutils-r2, and pkg_postinst is unnecessary" |
1215 |
+} |
1216 |
+ |
1217 |
+distutils_pkg_postrm() { |
1218 |
+ die "${FUNCNAME}() is invalid for distutils-r2, and pkg_postrm is unnecessary" |
1219 |
+} |
1220 |
+ |
1221 |
+_DISTUTILS_R2=1 |
1222 |
+fi |
1223 |
diff --git a/eclass/python-any-r2.eclass b/eclass/python-any-r2.eclass |
1224 |
new file mode 100644 |
1225 |
index 000000000000..cf70f23f69d5 |
1226 |
--- /dev/null |
1227 |
+++ b/eclass/python-any-r2.eclass |
1228 |
@@ -0,0 +1,357 @@ |
1229 |
+# Copyright 1999-2020 Gentoo Authors |
1230 |
+# Distributed under the terms of the GNU General Public License v2 |
1231 |
+ |
1232 |
+# @ECLASS: python-any-r2.eclass |
1233 |
+# @MAINTAINER: |
1234 |
+# Python team <python@g.o> |
1235 |
+# @AUTHOR: |
1236 |
+# Author: Michał Górny <mgorny@g.o> |
1237 |
+# @SUPPORTED_EAPIS: 5 6 7 |
1238 |
+# @BLURB: An eclass for packages having build-time dependency on Python. |
1239 |
+# @DESCRIPTION: |
1240 |
+# A minimal eclass for packages which need any Python interpreter |
1241 |
+# installed without a need for explicit choice and invariability. |
1242 |
+# This usually involves packages requiring Python at build-time |
1243 |
+# but having no other relevance to it. |
1244 |
+# |
1245 |
+# This eclass provides a minimal PYTHON_DEPS variable with a dependency |
1246 |
+# string on any of the supported Python implementations. It also exports |
1247 |
+# pkg_setup() which finds the best supported implementation and sets it |
1248 |
+# as the active one. |
1249 |
+# |
1250 |
+# Optionally, you can define a python_check_deps() function. It will |
1251 |
+# be called by the eclass with EPYTHON set to each matching Python |
1252 |
+# implementation and it is expected to check whether the implementation |
1253 |
+# fulfills the package requirements. You can use the locally exported |
1254 |
+# PYTHON_USEDEP to check USE-dependencies of relevant packages. It |
1255 |
+# should return a true value (0) if the Python implementation fulfills |
1256 |
+# the requirements, a false value (non-zero) otherwise. |
1257 |
+# |
1258 |
+# Please note that python-any-r2 will always inherit python-utils-r2 |
1259 |
+# as well. Thus, all the functions defined there can be used in the |
1260 |
+# packages using python-any-r2, and there is no need ever to inherit |
1261 |
+# both. |
1262 |
+ |
1263 |
+case "${EAPI:-0}" in |
1264 |
+ [0-4]) die "Unsupported EAPI=${EAPI:-0} (too old) for ${ECLASS}" ;; |
1265 |
+ [5-7]) ;; |
1266 |
+ *) die "Unsupported EAPI=${EAPI} (unknown) for ${ECLASS}" ;; |
1267 |
+esac |
1268 |
+ |
1269 |
+if [[ ! ${_PYTHON_ANY_R2} ]]; then |
1270 |
+ |
1271 |
+if [[ ${_PYTHON_R2} ]]; then |
1272 |
+ die 'python-any-r2.eclass can not be used with python-r2.eclass.' |
1273 |
+elif [[ ${_PYTHON_SINGLE_R2} ]]; then |
1274 |
+ die 'python-any-r2.eclass can not be used with python-single-r2.eclass.' |
1275 |
+fi |
1276 |
+ |
1277 |
+inherit python-utils-r2 |
1278 |
+ |
1279 |
+fi |
1280 |
+ |
1281 |
+EXPORT_FUNCTIONS pkg_setup |
1282 |
+ |
1283 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT |
1284 |
+# @REQUIRED |
1285 |
+# @DESCRIPTION: |
1286 |
+# This variable contains a list of Python implementations the package |
1287 |
+# supports. It must be set before the `inherit' call. It has to be |
1288 |
+# an array. |
1289 |
+# |
1290 |
+# Example: |
1291 |
+# @CODE |
1292 |
+# PYTHON_COMPAT=( python{2_5,2_6,2_7} ) |
1293 |
+# @CODE |
1294 |
+ |
1295 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT_OVERRIDE |
1296 |
+# @INTERNAL |
1297 |
+# @DESCRIPTION: |
1298 |
+# This variable can be used when working with ebuilds to override |
1299 |
+# the in-ebuild PYTHON_COMPAT. It is a string naming the implementation |
1300 |
+# which will be used to build the package. It needs to be specified |
1301 |
+# in the calling environment, and not in ebuilds. |
1302 |
+# |
1303 |
+# It should be noted that in order to preserve metadata immutability, |
1304 |
+# PYTHON_COMPAT_OVERRIDE does not affect dependencies. The value of |
1305 |
+# EPYTHON and eselect-python preferences are ignored. Dependencies need |
1306 |
+# to be satisfied manually. |
1307 |
+# |
1308 |
+# Example: |
1309 |
+# @CODE |
1310 |
+# PYTHON_COMPAT_OVERRIDE='pypy' emerge -1v dev-python/bar |
1311 |
+# @CODE |
1312 |
+ |
1313 |
+# @ECLASS-VARIABLE: PYTHON_REQ_USE |
1314 |
+# @DEFAULT_UNSET |
1315 |
+# @DESCRIPTION: |
1316 |
+# The list of USEflags required to be enabled on the Python |
1317 |
+# implementations, formed as a USE-dependency string. It should be valid |
1318 |
+# for all implementations in PYTHON_COMPAT, so it may be necessary to |
1319 |
+# use USE defaults. |
1320 |
+# |
1321 |
+# Example: |
1322 |
+# @CODE |
1323 |
+# PYTHON_REQ_USE="gdbm,ncurses(-)?" |
1324 |
+# @CODE |
1325 |
+# |
1326 |
+# It will cause the Python dependencies to look like: |
1327 |
+# @CODE |
1328 |
+# || ( dev-lang/python:X.Y[gdbm,ncurses(-)?] ... ) |
1329 |
+# @CODE |
1330 |
+ |
1331 |
+# @ECLASS-VARIABLE: PYTHON_DEPS |
1332 |
+# @DESCRIPTION: |
1333 |
+# This is an eclass-generated Python dependency string for all |
1334 |
+# implementations listed in PYTHON_COMPAT. |
1335 |
+# |
1336 |
+# Any of the supported interpreters will satisfy the dependency. |
1337 |
+# |
1338 |
+# Example use: |
1339 |
+# @CODE |
1340 |
+# DEPEND="${RDEPEND} |
1341 |
+# ${PYTHON_DEPS}" |
1342 |
+# @CODE |
1343 |
+# |
1344 |
+# Example value: |
1345 |
+# @CODE |
1346 |
+# || ( dev-lang/python:2.7[gdbm] |
1347 |
+# dev-lang/python:2.6[gdbm] ) |
1348 |
+# @CODE |
1349 |
+ |
1350 |
+# @ECLASS-VARIABLE: PYTHON_USEDEP |
1351 |
+# @DESCRIPTION: |
1352 |
+# An eclass-generated USE-dependency string for the currently tested |
1353 |
+# implementation. It is set locally for python_check_deps() call. |
1354 |
+# |
1355 |
+# The generate USE-flag list is compatible with packages using python-r2, |
1356 |
+# python-single-r2 and python-distutils-ng eclasses. It must not be used |
1357 |
+# on packages using python.eclass. |
1358 |
+# |
1359 |
+# Example use: |
1360 |
+# @CODE |
1361 |
+# python_check_deps() { |
1362 |
+# has_version "dev-python/foo[${PYTHON_USEDEP}]" |
1363 |
+# } |
1364 |
+# @CODE |
1365 |
+# |
1366 |
+# Example value: |
1367 |
+# @CODE |
1368 |
+# python_targets_python2_7(-)?,python_single_target_python2_7(+)? |
1369 |
+# @CODE |
1370 |
+ |
1371 |
+_python_any_set_globals() { |
1372 |
+ local usestr deps i PYTHON_PKG_DEP |
1373 |
+ [[ ${PYTHON_REQ_USE} ]] && usestr="[${PYTHON_REQ_USE}]" |
1374 |
+ |
1375 |
+ _python_set_impls |
1376 |
+ |
1377 |
+ for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
1378 |
+ python_export "${i}" PYTHON_PKG_DEP |
1379 |
+ |
1380 |
+ # note: need to strip '=' slot operator for || deps |
1381 |
+ deps="${PYTHON_PKG_DEP/:0=/:0} ${deps}" |
1382 |
+ done |
1383 |
+ deps="|| ( ${deps})" |
1384 |
+ |
1385 |
+ if [[ ${PYTHON_DEPS+1} ]]; then |
1386 |
+ if [[ ${PYTHON_DEPS} != "${deps}" ]]; then |
1387 |
+ eerror "PYTHON_DEPS have changed between inherits (PYTHON_REQ_USE?)!" |
1388 |
+ eerror "Before: ${PYTHON_DEPS}" |
1389 |
+ eerror "Now : ${deps}" |
1390 |
+ die "PYTHON_DEPS integrity check failed" |
1391 |
+ fi |
1392 |
+ else |
1393 |
+ PYTHON_DEPS=${deps} |
1394 |
+ readonly PYTHON_DEPS |
1395 |
+ fi |
1396 |
+ |
1397 |
+ if [[ ! ${PYTHON_REQUIRED_USE+1} ]]; then |
1398 |
+ # fake var to catch mistaken usage |
1399 |
+ PYTHON_REQUIRED_USE='I-DO-NOT-EXIST-IN-PYTHON-ANY-R1' |
1400 |
+ readonly PYTHON_REQUIRED_USE |
1401 |
+ fi |
1402 |
+} |
1403 |
+_python_any_set_globals |
1404 |
+unset -f _python_any_set_globals |
1405 |
+ |
1406 |
+if [[ ! ${_PYTHON_ANY_R2} ]]; then |
1407 |
+ |
1408 |
+# @FUNCTION: python_gen_any_dep |
1409 |
+# @USAGE: <dependency-block> |
1410 |
+# @DESCRIPTION: |
1411 |
+# Generate an any-of dependency that enforces a version match between |
1412 |
+# the Python interpreter and Python packages. <dependency-block> needs |
1413 |
+# to list one or more dependencies with verbatim '${PYTHON_USEDEP}' |
1414 |
+# references (quoted!) that will get expanded inside the function. |
1415 |
+# |
1416 |
+# This should be used along with an appropriate python_check_deps() |
1417 |
+# that checks which of the any-of blocks were matched. |
1418 |
+# |
1419 |
+# Example use: |
1420 |
+# @CODE |
1421 |
+# DEPEND="$(python_gen_any_dep ' |
1422 |
+# dev-python/foo[${PYTHON_USEDEP}] |
1423 |
+# || ( dev-python/bar[${PYTHON_USEDEP}] |
1424 |
+# dev-python/baz[${PYTHON_USEDEP}] )')" |
1425 |
+# |
1426 |
+# python_check_deps() { |
1427 |
+# has_version "dev-python/foo[${PYTHON_USEDEP}]" \ |
1428 |
+# && { has_version "dev-python/bar[${PYTHON_USEDEP}]" \ |
1429 |
+# || has_version "dev-python/baz[${PYTHON_USEDEP}]"; } |
1430 |
+# } |
1431 |
+# @CODE |
1432 |
+# |
1433 |
+# Example value: |
1434 |
+# @CODE |
1435 |
+# || ( |
1436 |
+# ( |
1437 |
+# dev-lang/python:2.7 |
1438 |
+# dev-python/foo[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] |
1439 |
+# || ( dev-python/bar[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] |
1440 |
+# dev-python/baz[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] ) |
1441 |
+# ) |
1442 |
+# ( |
1443 |
+# dev-lang/python:3.3 |
1444 |
+# dev-python/foo[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] |
1445 |
+# || ( dev-python/bar[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] |
1446 |
+# dev-python/baz[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] ) |
1447 |
+# ) |
1448 |
+# ) |
1449 |
+# @CODE |
1450 |
+python_gen_any_dep() { |
1451 |
+ debug-print-function ${FUNCNAME} "${@}" |
1452 |
+ |
1453 |
+ local depstr=${1} |
1454 |
+ [[ ${depstr} ]] || die "No dependency string provided" |
1455 |
+ |
1456 |
+ local i PYTHON_PKG_DEP out= |
1457 |
+ for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
1458 |
+ local PYTHON_USEDEP="python_targets_${i}(-),python_single_target_${i}(+)" |
1459 |
+ python_export "${i}" PYTHON_PKG_DEP |
1460 |
+ |
1461 |
+ local i_depstr=${depstr//\$\{PYTHON_USEDEP\}/${PYTHON_USEDEP}} |
1462 |
+ # note: need to strip '=' slot operator for || deps |
1463 |
+ out="( ${PYTHON_PKG_DEP%=} ${i_depstr} ) ${out}" |
1464 |
+ done |
1465 |
+ echo "|| ( ${out})" |
1466 |
+} |
1467 |
+ |
1468 |
+# @FUNCTION: _python_EPYTHON_supported |
1469 |
+# @USAGE: <epython> |
1470 |
+# @INTERNAL |
1471 |
+# @DESCRIPTION: |
1472 |
+# Check whether the specified implementation is supported by package |
1473 |
+# (specified in PYTHON_COMPAT). Calls python_check_deps() if declared. |
1474 |
+_python_EPYTHON_supported() { |
1475 |
+ debug-print-function ${FUNCNAME} "${@}" |
1476 |
+ |
1477 |
+ local EPYTHON=${1} |
1478 |
+ local i=${EPYTHON/./_} |
1479 |
+ |
1480 |
+ case "${i}" in |
1481 |
+ python*|jython*|pypy*) |
1482 |
+ ;; |
1483 |
+ *) |
1484 |
+ ewarn "Invalid EPYTHON: ${EPYTHON}" |
1485 |
+ return 1 |
1486 |
+ ;; |
1487 |
+ esac |
1488 |
+ |
1489 |
+ if has "${i}" "${_PYTHON_SUPPORTED_IMPLS[@]}"; then |
1490 |
+ if python_is_installed "${i}"; then |
1491 |
+ if declare -f python_check_deps >/dev/null; then |
1492 |
+ local PYTHON_USEDEP="python_targets_${i}(-),python_single_target_${i}(+)" |
1493 |
+ python_check_deps |
1494 |
+ return ${?} |
1495 |
+ fi |
1496 |
+ |
1497 |
+ return 0 |
1498 |
+ fi |
1499 |
+ elif ! has "${i}" "${_PYTHON_ALL_IMPLS[@]}"; then |
1500 |
+ ewarn "Invalid EPYTHON: ${EPYTHON}" |
1501 |
+ fi |
1502 |
+ return 1 |
1503 |
+} |
1504 |
+ |
1505 |
+# @FUNCTION: python_setup |
1506 |
+# @DESCRIPTION: |
1507 |
+# Determine what the best installed (and supported) Python |
1508 |
+# implementation is, and set the Python build environment up for it. |
1509 |
+# |
1510 |
+# This function will call python_check_deps() if defined. |
1511 |
+python_setup() { |
1512 |
+ debug-print-function ${FUNCNAME} "${@}" |
1513 |
+ |
1514 |
+ # support developer override |
1515 |
+ if [[ ${PYTHON_COMPAT_OVERRIDE} ]]; then |
1516 |
+ local impls=( ${PYTHON_COMPAT_OVERRIDE} ) |
1517 |
+ [[ ${#impls[@]} -eq 1 ]] || die "PYTHON_COMPAT_OVERRIDE must name exactly one implementation for python-any-r2" |
1518 |
+ |
1519 |
+ ewarn "WARNING: PYTHON_COMPAT_OVERRIDE in effect. The following Python" |
1520 |
+ ewarn "implementation will be used:" |
1521 |
+ ewarn |
1522 |
+ ewarn " ${PYTHON_COMPAT_OVERRIDE}" |
1523 |
+ ewarn |
1524 |
+ ewarn "Dependencies won't be satisfied, and EPYTHON/eselect-python will be ignored." |
1525 |
+ |
1526 |
+ python_export "${impls[0]}" EPYTHON PYTHON |
1527 |
+ python_wrapper_setup |
1528 |
+ return |
1529 |
+ fi |
1530 |
+ |
1531 |
+ # first, try ${EPYTHON}... maybe it's good enough for us. |
1532 |
+ if [[ ${EPYTHON} ]]; then |
1533 |
+ if _python_EPYTHON_supported "${EPYTHON}"; then |
1534 |
+ python_export EPYTHON PYTHON |
1535 |
+ python_wrapper_setup |
1536 |
+ return |
1537 |
+ fi |
1538 |
+ fi |
1539 |
+ |
1540 |
+ # then, try eselect-python |
1541 |
+ local variant i |
1542 |
+ for variant in '' '--python2' '--python3'; do |
1543 |
+ i=$(eselect python --show ${variant} 2>/dev/null) |
1544 |
+ |
1545 |
+ if [[ ! ${i} ]]; then |
1546 |
+ # no eselect-python? |
1547 |
+ break |
1548 |
+ elif _python_EPYTHON_supported "${i}"; then |
1549 |
+ python_export "${i}" EPYTHON PYTHON |
1550 |
+ python_wrapper_setup |
1551 |
+ return |
1552 |
+ fi |
1553 |
+ done |
1554 |
+ |
1555 |
+ # fallback to best installed impl. |
1556 |
+ # (reverse iteration over _PYTHON_SUPPORTED_IMPLS) |
1557 |
+ for (( i = ${#_PYTHON_SUPPORTED_IMPLS[@]} - 1; i >= 0; i-- )); do |
1558 |
+ python_export "${_PYTHON_SUPPORTED_IMPLS[i]}" EPYTHON PYTHON |
1559 |
+ if _python_EPYTHON_supported "${EPYTHON}"; then |
1560 |
+ python_wrapper_setup |
1561 |
+ return |
1562 |
+ fi |
1563 |
+ done |
1564 |
+ |
1565 |
+ eerror "No Python implementation found for the build. This is usually" |
1566 |
+ eerror "a bug in the ebuild. Please report it to bugs.gentoo.org" |
1567 |
+ eerror "along with the build log." |
1568 |
+ echo |
1569 |
+ die "No supported Python implementation installed." |
1570 |
+} |
1571 |
+ |
1572 |
+# @FUNCTION: python-any-r2_pkg_setup |
1573 |
+# @DESCRIPTION: |
1574 |
+# Runs python_setup during from-source installs. |
1575 |
+# |
1576 |
+# In a binary package installs is a no-op. If you need Python in pkg_* |
1577 |
+# phases of a binary package, call python_setup directly. |
1578 |
+python-any-r2_pkg_setup() { |
1579 |
+ debug-print-function ${FUNCNAME} "${@}" |
1580 |
+ |
1581 |
+ [[ ${MERGE_TYPE} != binary ]] && python_setup |
1582 |
+} |
1583 |
+ |
1584 |
+_PYTHON_ANY_R2=1 |
1585 |
+fi |
1586 |
diff --git a/eclass/python-r2.eclass b/eclass/python-r2.eclass |
1587 |
new file mode 100644 |
1588 |
index 000000000000..8bf0b1a1ac29 |
1589 |
--- /dev/null |
1590 |
+++ b/eclass/python-r2.eclass |
1591 |
@@ -0,0 +1,825 @@ |
1592 |
+# Copyright 1999-2020 Gentoo Authors |
1593 |
+# Distributed under the terms of the GNU General Public License v2 |
1594 |
+ |
1595 |
+# @ECLASS: python-r2.eclass |
1596 |
+# @MAINTAINER: |
1597 |
+# Python team <python@g.o> |
1598 |
+# @AUTHOR: |
1599 |
+# Author: Michał Górny <mgorny@g.o> |
1600 |
+# @SUPPORTED_EAPIS: 5 6 7 |
1601 |
+# @BLURB: A common, simple eclass for Python packages. |
1602 |
+# @DESCRIPTION: |
1603 |
+# A common eclass providing helper functions to build and install |
1604 |
+# packages supporting being installed for multiple Python |
1605 |
+# implementations. |
1606 |
+# |
1607 |
+# This eclass sets correct IUSE. Modification of REQUIRED_USE has to |
1608 |
+# be done by the author of the ebuild (but PYTHON_REQUIRED_USE is |
1609 |
+# provided for convenience, see below). python-r2 exports PYTHON_DEPS |
1610 |
+# and PYTHON_USEDEP so you can create correct dependencies for your |
1611 |
+# package easily. It also provides methods to easily run a command for |
1612 |
+# each enabled Python implementation and duplicate the sources for them. |
1613 |
+# |
1614 |
+# Please note that python-r2 will always inherit python-utils-r2 as |
1615 |
+# well. Thus, all the functions defined there can be used |
1616 |
+# in the packages using python-r2, and there is no need ever to inherit |
1617 |
+# both. |
1618 |
+ |
1619 |
+case "${EAPI:-0}" in |
1620 |
+ 0|1|2|3|4) |
1621 |
+ die "Unsupported EAPI=${EAPI:-0} (too old) for ${ECLASS}" |
1622 |
+ ;; |
1623 |
+ 5|6|7) |
1624 |
+ # EAPI=5 is required for sane USE_EXPAND dependencies |
1625 |
+ ;; |
1626 |
+ *) |
1627 |
+ die "Unsupported EAPI=${EAPI} (unknown) for ${ECLASS}" |
1628 |
+ ;; |
1629 |
+esac |
1630 |
+ |
1631 |
+if [[ ! ${_PYTHON_R2} ]]; then |
1632 |
+ |
1633 |
+if [[ ${_PYTHON_SINGLE_R2} ]]; then |
1634 |
+ die 'python-r2.eclass can not be used with python-single-r2.eclass.' |
1635 |
+elif [[ ${_PYTHON_ANY_R2} ]]; then |
1636 |
+ die 'python-r2.eclass can not be used with python-any-r2.eclass.' |
1637 |
+fi |
1638 |
+ |
1639 |
+[[ ${EAPI} == [45] ]] && inherit eutils |
1640 |
+inherit multibuild python-utils-r2 |
1641 |
+ |
1642 |
+fi |
1643 |
+ |
1644 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT |
1645 |
+# @REQUIRED |
1646 |
+# @DESCRIPTION: |
1647 |
+# This variable contains a list of Python implementations the package |
1648 |
+# supports. It must be set before the `inherit' call. It has to be |
1649 |
+# an array. |
1650 |
+# |
1651 |
+# Example: |
1652 |
+# @CODE |
1653 |
+# PYTHON_COMPAT=( python2_7 python3_3 python3_4 ) |
1654 |
+# @CODE |
1655 |
+# |
1656 |
+# Please note that you can also use bash brace expansion if you like: |
1657 |
+# @CODE |
1658 |
+# PYTHON_COMPAT=( python2_7 python3_{3,4} ) |
1659 |
+# @CODE |
1660 |
+ |
1661 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT_OVERRIDE |
1662 |
+# @INTERNAL |
1663 |
+# @DESCRIPTION: |
1664 |
+# This variable can be used when working with ebuilds to override |
1665 |
+# the in-ebuild PYTHON_COMPAT. It is a string listing all |
1666 |
+# the implementations which package will be built for. It need be |
1667 |
+# specified in the calling environment, and not in ebuilds. |
1668 |
+# |
1669 |
+# It should be noted that in order to preserve metadata immutability, |
1670 |
+# PYTHON_COMPAT_OVERRIDE does not affect IUSE nor dependencies. |
1671 |
+# The state of PYTHON_TARGETS is ignored, and all the implementations |
1672 |
+# in PYTHON_COMPAT_OVERRIDE are built. Dependencies need to be satisfied |
1673 |
+# manually. |
1674 |
+# |
1675 |
+# Example: |
1676 |
+# @CODE |
1677 |
+# PYTHON_COMPAT_OVERRIDE='pypy python3_3' emerge -1v dev-python/foo |
1678 |
+# @CODE |
1679 |
+ |
1680 |
+# @ECLASS-VARIABLE: PYTHON_REQ_USE |
1681 |
+# @DEFAULT_UNSET |
1682 |
+# @DESCRIPTION: |
1683 |
+# The list of USEflags required to be enabled on the chosen Python |
1684 |
+# implementations, formed as a USE-dependency string. It should be valid |
1685 |
+# for all implementations in PYTHON_COMPAT, so it may be necessary to |
1686 |
+# use USE defaults. |
1687 |
+# |
1688 |
+# This should be set before calling `inherit'. |
1689 |
+# |
1690 |
+# Example: |
1691 |
+# @CODE |
1692 |
+# PYTHON_REQ_USE="gdbm,ncurses(-)?" |
1693 |
+# @CODE |
1694 |
+# |
1695 |
+# It will cause the Python dependencies to look like: |
1696 |
+# @CODE |
1697 |
+# python_targets_pythonX_Y? ( dev-lang/python:X.Y[gdbm,ncurses(-)?] ) |
1698 |
+# @CODE |
1699 |
+ |
1700 |
+# @ECLASS-VARIABLE: PYTHON_DEPS |
1701 |
+# @DESCRIPTION: |
1702 |
+# This is an eclass-generated Python dependency string for all |
1703 |
+# implementations listed in PYTHON_COMPAT. |
1704 |
+# |
1705 |
+# Example use: |
1706 |
+# @CODE |
1707 |
+# RDEPEND="${PYTHON_DEPS} |
1708 |
+# dev-foo/mydep" |
1709 |
+# DEPEND="${RDEPEND}" |
1710 |
+# @CODE |
1711 |
+# |
1712 |
+# Example value: |
1713 |
+# @CODE |
1714 |
+# dev-lang/python-exec:= |
1715 |
+# python_targets_python2_7? ( dev-lang/python:2.7[gdbm] ) |
1716 |
+# python_targets_pypy? ( dev-python/pypy[gdbm] ) |
1717 |
+# @CODE |
1718 |
+ |
1719 |
+# @ECLASS-VARIABLE: PYTHON_USEDEP |
1720 |
+# @DESCRIPTION: |
1721 |
+# This is an eclass-generated USE-dependency string which can be used to |
1722 |
+# depend on another Python package being built for the same Python |
1723 |
+# implementations. |
1724 |
+# |
1725 |
+# The generate USE-flag list is compatible with packages using python-r2 |
1726 |
+# and python-distutils-ng eclasses. It must not be used on packages |
1727 |
+# using python.eclass. |
1728 |
+# |
1729 |
+# Example use: |
1730 |
+# @CODE |
1731 |
+# RDEPEND="dev-python/foo[${PYTHON_USEDEP}]" |
1732 |
+# @CODE |
1733 |
+# |
1734 |
+# Example value: |
1735 |
+# @CODE |
1736 |
+# python_targets_python2_7(-)?,python_targets_python3_4(-)? |
1737 |
+# @CODE |
1738 |
+ |
1739 |
+# @ECLASS-VARIABLE: PYTHON_REQUIRED_USE |
1740 |
+# @DESCRIPTION: |
1741 |
+# This is an eclass-generated required-use expression which ensures at |
1742 |
+# least one Python implementation has been enabled. |
1743 |
+# |
1744 |
+# This expression should be utilized in an ebuild by including it in |
1745 |
+# REQUIRED_USE, optionally behind a use flag. |
1746 |
+# |
1747 |
+# Example use: |
1748 |
+# @CODE |
1749 |
+# REQUIRED_USE="python? ( ${PYTHON_REQUIRED_USE} )" |
1750 |
+# @CODE |
1751 |
+# |
1752 |
+# Example value: |
1753 |
+# @CODE |
1754 |
+# || ( python_targets_python2_7 python_targets_python3_4 ) |
1755 |
+# @CODE |
1756 |
+ |
1757 |
+_python_set_globals() { |
1758 |
+ local deps i PYTHON_PKG_DEP |
1759 |
+ |
1760 |
+ _python_set_impls |
1761 |
+ |
1762 |
+ for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
1763 |
+ python_export "${i}" PYTHON_PKG_DEP |
1764 |
+ deps+="python_targets_${i}? ( ${PYTHON_PKG_DEP} ) " |
1765 |
+ done |
1766 |
+ |
1767 |
+ local flags=( "${_PYTHON_SUPPORTED_IMPLS[@]/#/python_targets_}" ) |
1768 |
+ local optflags=${flags[@]/%/(-)?} |
1769 |
+ |
1770 |
+ # A nice QA trick here. Since a python-single-r2 package has to have |
1771 |
+ # at least one PYTHON_SINGLE_TARGET enabled (REQUIRED_USE), |
1772 |
+ # the following check will always fail on those packages. Therefore, |
1773 |
+ # it should prevent developers from mistakenly depending on packages |
1774 |
+ # not supporting multiple Python implementations. |
1775 |
+ |
1776 |
+ local flags_st=( "${_PYTHON_SUPPORTED_IMPLS[@]/#/-python_single_target_}" ) |
1777 |
+ optflags+=,${flags_st[@]/%/(-)} |
1778 |
+ local requse="|| ( ${flags[*]} )" |
1779 |
+ local usedep=${optflags// /,} |
1780 |
+ |
1781 |
+ # 1) well, python-exec would suffice as an RDEP |
1782 |
+ # but no point in making this overcomplex, BDEP doesn't hurt anyone |
1783 |
+ # 2) python-exec should be built with all targets forced anyway |
1784 |
+ # but if new targets were added, we may need to force a rebuild |
1785 |
+ deps+=">=dev-lang/python-exec-2:=[${usedep}]" |
1786 |
+ |
1787 |
+ if [[ ${PYTHON_DEPS+1} ]]; then |
1788 |
+ # IUSE is magical, so we can't really check it |
1789 |
+ # (but we verify PYTHON_COMPAT already) |
1790 |
+ |
1791 |
+ if [[ ${PYTHON_DEPS} != "${deps}" ]]; then |
1792 |
+ eerror "PYTHON_DEPS have changed between inherits (PYTHON_REQ_USE?)!" |
1793 |
+ eerror "Before: ${PYTHON_DEPS}" |
1794 |
+ eerror "Now : ${deps}" |
1795 |
+ die "PYTHON_DEPS integrity check failed" |
1796 |
+ fi |
1797 |
+ |
1798 |
+ # these two are formality -- they depend on PYTHON_COMPAT only |
1799 |
+ if [[ ${PYTHON_REQUIRED_USE} != ${requse} ]]; then |
1800 |
+ eerror "PYTHON_REQUIRED_USE have changed between inherits!" |
1801 |
+ eerror "Before: ${PYTHON_REQUIRED_USE}" |
1802 |
+ eerror "Now : ${requse}" |
1803 |
+ die "PYTHON_REQUIRED_USE integrity check failed" |
1804 |
+ fi |
1805 |
+ |
1806 |
+ if [[ ${PYTHON_USEDEP} != "${usedep}" ]]; then |
1807 |
+ eerror "PYTHON_USEDEP have changed between inherits!" |
1808 |
+ eerror "Before: ${PYTHON_USEDEP}" |
1809 |
+ eerror "Now : ${usedep}" |
1810 |
+ die "PYTHON_USEDEP integrity check failed" |
1811 |
+ fi |
1812 |
+ else |
1813 |
+ IUSE=${flags[*]} |
1814 |
+ |
1815 |
+ PYTHON_DEPS=${deps} |
1816 |
+ PYTHON_REQUIRED_USE=${requse} |
1817 |
+ PYTHON_USEDEP=${usedep} |
1818 |
+ readonly PYTHON_DEPS PYTHON_REQUIRED_USE |
1819 |
+ fi |
1820 |
+} |
1821 |
+_python_set_globals |
1822 |
+unset -f _python_set_globals |
1823 |
+ |
1824 |
+if [[ ! ${_PYTHON_R2} ]]; then |
1825 |
+ |
1826 |
+# @FUNCTION: _python_validate_useflags |
1827 |
+# @INTERNAL |
1828 |
+# @DESCRIPTION: |
1829 |
+# Enforce the proper setting of PYTHON_TARGETS, if PYTHON_COMPAT_OVERRIDE |
1830 |
+# is not in effect. If it is, just warn that the flags will be ignored. |
1831 |
+_python_validate_useflags() { |
1832 |
+ debug-print-function ${FUNCNAME} "${@}" |
1833 |
+ |
1834 |
+ if [[ ${PYTHON_COMPAT_OVERRIDE} ]]; then |
1835 |
+ if [[ ! ${_PYTHON_COMPAT_OVERRIDE_WARNED} ]]; then |
1836 |
+ ewarn "WARNING: PYTHON_COMPAT_OVERRIDE in effect. The following Python" |
1837 |
+ ewarn "implementations will be enabled:" |
1838 |
+ ewarn |
1839 |
+ ewarn " ${PYTHON_COMPAT_OVERRIDE}" |
1840 |
+ ewarn |
1841 |
+ ewarn "Dependencies won't be satisfied, and PYTHON_TARGETS will be ignored." |
1842 |
+ _PYTHON_COMPAT_OVERRIDE_WARNED=1 |
1843 |
+ fi |
1844 |
+ # we do not use flags with PCO |
1845 |
+ return |
1846 |
+ fi |
1847 |
+ |
1848 |
+ local i |
1849 |
+ |
1850 |
+ for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
1851 |
+ use "python_targets_${i}" && return 0 |
1852 |
+ done |
1853 |
+ |
1854 |
+ eerror "No Python implementation selected for the build. Please add one" |
1855 |
+ eerror "of the following values to your PYTHON_TARGETS (in make.conf):" |
1856 |
+ eerror |
1857 |
+ eerror "${PYTHON_COMPAT[@]}" |
1858 |
+ echo |
1859 |
+ die "No supported Python implementation in PYTHON_TARGETS." |
1860 |
+} |
1861 |
+ |
1862 |
+# @FUNCTION: _python_gen_usedep |
1863 |
+# @INTERNAL |
1864 |
+# @USAGE: [<pattern>...] |
1865 |
+# @DESCRIPTION: |
1866 |
+# Output a USE dependency string for Python implementations which |
1867 |
+# are both in PYTHON_COMPAT and match any of the patterns passed |
1868 |
+# as parameters to the function. |
1869 |
+# |
1870 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
1871 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
1872 |
+# appropriately all enabled Python 2/3 implementations (alike |
1873 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
1874 |
+# to prevent accidental shell filename expansion. |
1875 |
+# |
1876 |
+# This is an internal function used to implement python_gen_cond_dep |
1877 |
+# and deprecated python_gen_usedep. |
1878 |
+_python_gen_usedep() { |
1879 |
+ debug-print-function ${FUNCNAME} "${@}" |
1880 |
+ |
1881 |
+ local impl matches=() |
1882 |
+ |
1883 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
1884 |
+ if _python_impl_matches "${impl}" "${@}"; then |
1885 |
+ matches+=( |
1886 |
+ "python_targets_${impl}(-)?" |
1887 |
+ "-python_single_target_${impl}(-)" |
1888 |
+ ) |
1889 |
+ fi |
1890 |
+ done |
1891 |
+ |
1892 |
+ [[ ${matches[@]} ]] || die "No supported implementations match python_gen_usedep patterns: ${@}" |
1893 |
+ |
1894 |
+ local out=${matches[@]} |
1895 |
+ echo "${out// /,}" |
1896 |
+} |
1897 |
+ |
1898 |
+# @FUNCTION: python_gen_usedep |
1899 |
+# @USAGE: <pattern> [...] |
1900 |
+# @DESCRIPTION: |
1901 |
+# DEPRECATED. Please use python_gen_cond_dep instead. |
1902 |
+# |
1903 |
+# Output a USE dependency string for Python implementations which |
1904 |
+# are both in PYTHON_COMPAT and match any of the patterns passed |
1905 |
+# as parameters to the function. |
1906 |
+# |
1907 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
1908 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
1909 |
+# appropriately all enabled Python 2/3 implementations (alike |
1910 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
1911 |
+# to prevent accidental shell filename expansion. |
1912 |
+# |
1913 |
+# When all implementations are requested, please use ${PYTHON_USEDEP} |
1914 |
+# instead. Please also remember to set an appropriate REQUIRED_USE |
1915 |
+# to avoid ineffective USE flags. |
1916 |
+# |
1917 |
+# Example: |
1918 |
+# @CODE |
1919 |
+# PYTHON_COMPAT=( python{2_7,3_4} ) |
1920 |
+# DEPEND="doc? ( dev-python/epydoc[$(python_gen_usedep 'python2*')] )" |
1921 |
+# @CODE |
1922 |
+# |
1923 |
+# It will cause the dependency to look like: |
1924 |
+# @CODE |
1925 |
+# DEPEND="doc? ( dev-python/epydoc[python_targets_python2_7?] )" |
1926 |
+# @CODE |
1927 |
+python_gen_usedep() { |
1928 |
+ debug-print-function ${FUNCNAME} "${@}" |
1929 |
+ |
1930 |
+ # output only once, during some reasonable phase |
1931 |
+ # (avoid spamming cache regen runs) |
1932 |
+ if [[ ${EBUILD_PHASE} == setup ]]; then |
1933 |
+ eqawarn "python_gen_usedep() is deprecated. Please use python_gen_cond_dep instead." |
1934 |
+ fi |
1935 |
+ _python_gen_usedep "${@}" |
1936 |
+} |
1937 |
+ |
1938 |
+# @FUNCTION: python_gen_useflags |
1939 |
+# @USAGE: [<pattern>...] |
1940 |
+# @DESCRIPTION: |
1941 |
+# Output a list of USE flags for Python implementations which |
1942 |
+# are both in PYTHON_COMPAT and match any of the patterns passed |
1943 |
+# as parameters to the function. |
1944 |
+# |
1945 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
1946 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
1947 |
+# appropriately all enabled Python 2/3 implementations (alike |
1948 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
1949 |
+# to prevent accidental shell filename expansion. |
1950 |
+# |
1951 |
+# Example: |
1952 |
+# @CODE |
1953 |
+# PYTHON_COMPAT=( python{2_7,3_4} ) |
1954 |
+# REQUIRED_USE="doc? ( || ( $(python_gen_useflags python2*) ) )" |
1955 |
+# @CODE |
1956 |
+# |
1957 |
+# It will cause the variable to look like: |
1958 |
+# @CODE |
1959 |
+# REQUIRED_USE="doc? ( || ( python_targets_python2_7 ) )" |
1960 |
+# @CODE |
1961 |
+python_gen_useflags() { |
1962 |
+ debug-print-function ${FUNCNAME} "${@}" |
1963 |
+ |
1964 |
+ local impl matches=() |
1965 |
+ |
1966 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
1967 |
+ if _python_impl_matches "${impl}" "${@}"; then |
1968 |
+ matches+=( "python_targets_${impl}" ) |
1969 |
+ fi |
1970 |
+ done |
1971 |
+ |
1972 |
+ echo "${matches[@]}" |
1973 |
+} |
1974 |
+ |
1975 |
+# @FUNCTION: python_gen_cond_dep |
1976 |
+# @USAGE: <dependency> [<pattern>...] |
1977 |
+# @DESCRIPTION: |
1978 |
+# Output a list of <dependency>-ies made conditional to USE flags |
1979 |
+# of Python implementations which are both in PYTHON_COMPAT and match |
1980 |
+# any of the patterns passed as the remaining parameters. |
1981 |
+# |
1982 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
1983 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
1984 |
+# appropriately all enabled Python 2/3 implementations (alike |
1985 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
1986 |
+# to prevent accidental shell filename expansion. |
1987 |
+# |
1988 |
+# In order to enforce USE constraints on the packages, verbatim |
1989 |
+# '${PYTHON_USEDEP}' (quoted!) may be placed in the dependency |
1990 |
+# specification. It will get expanded within the function into a proper |
1991 |
+# USE dependency string. |
1992 |
+# |
1993 |
+# Example: |
1994 |
+# @CODE |
1995 |
+# PYTHON_COMPAT=( python{2_7,3_{3,4}} pypy ) |
1996 |
+# RDEPEND="$(python_gen_cond_dep \ |
1997 |
+# 'dev-python/unittest2[${PYTHON_USEDEP}]' python2_7 pypy )" |
1998 |
+# @CODE |
1999 |
+# |
2000 |
+# It will cause the variable to look like: |
2001 |
+# @CODE |
2002 |
+# RDEPEND="python_targets_python2_7? ( |
2003 |
+# dev-python/unittest2[python_targets_python2_7?] ) |
2004 |
+# python_targets_pypy? ( |
2005 |
+# dev-python/unittest2[python_targets_pypy?] )" |
2006 |
+# @CODE |
2007 |
+python_gen_cond_dep() { |
2008 |
+ debug-print-function ${FUNCNAME} "${@}" |
2009 |
+ |
2010 |
+ local impl matches=() |
2011 |
+ local dep=${1} |
2012 |
+ shift |
2013 |
+ |
2014 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2015 |
+ if _python_impl_matches "${impl}" "${@}"; then |
2016 |
+ # substitute ${PYTHON_USEDEP} if used |
2017 |
+ # (since python_gen_usedep() will not return ${PYTHON_USEDEP} |
2018 |
+ # the code is run at most once) |
2019 |
+ if [[ ${dep} == *'${PYTHON_USEDEP}'* ]]; then |
2020 |
+ local usedep=$(_python_gen_usedep "${@}") |
2021 |
+ dep=${dep//\$\{PYTHON_USEDEP\}/${usedep}} |
2022 |
+ fi |
2023 |
+ |
2024 |
+ matches+=( "python_targets_${impl}? ( ${dep} )" ) |
2025 |
+ fi |
2026 |
+ done |
2027 |
+ |
2028 |
+ echo "${matches[@]}" |
2029 |
+} |
2030 |
+ |
2031 |
+# @FUNCTION: python_gen_impl_dep |
2032 |
+# @USAGE: [<requested-use-flags> [<impl-pattern>...]] |
2033 |
+# @DESCRIPTION: |
2034 |
+# Output a dependency on Python implementations with the specified USE |
2035 |
+# dependency string appended, or no USE dependency string if called |
2036 |
+# without the argument (or with empty argument). If any implementation |
2037 |
+# patterns are passed, the output dependencies will be generated only |
2038 |
+# for the implementations matching them. |
2039 |
+# |
2040 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2041 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2042 |
+# appropriately all enabled Python 2/3 implementations (alike |
2043 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2044 |
+# to prevent accidental shell filename expansion. |
2045 |
+# |
2046 |
+# Use this function when you need to request different USE flags |
2047 |
+# on the Python interpreter depending on package's USE flags. If you |
2048 |
+# only need a single set of interpreter USE flags, just set |
2049 |
+# PYTHON_REQ_USE and use ${PYTHON_DEPS} globally. |
2050 |
+# |
2051 |
+# Example: |
2052 |
+# @CODE |
2053 |
+# PYTHON_COMPAT=( python{2_7,3_{3,4}} pypy ) |
2054 |
+# RDEPEND="foo? ( $(python_gen_impl_dep 'xml(+)') )" |
2055 |
+# @CODE |
2056 |
+# |
2057 |
+# It will cause the variable to look like: |
2058 |
+# @CODE |
2059 |
+# RDEPEND="foo? ( |
2060 |
+# python_targets_python2_7? ( |
2061 |
+# dev-lang/python:2.7[xml(+)] ) |
2062 |
+# python_targets_pypy? ( |
2063 |
+# dev-python/pypy[xml(+)] ) )" |
2064 |
+# @CODE |
2065 |
+python_gen_impl_dep() { |
2066 |
+ debug-print-function ${FUNCNAME} "${@}" |
2067 |
+ |
2068 |
+ local impl matches=() |
2069 |
+ local PYTHON_REQ_USE=${1} |
2070 |
+ shift |
2071 |
+ |
2072 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2073 |
+ if _python_impl_matches "${impl}" "${@}"; then |
2074 |
+ local PYTHON_PKG_DEP |
2075 |
+ python_export "${impl}" PYTHON_PKG_DEP |
2076 |
+ matches+=( "python_targets_${impl}? ( ${PYTHON_PKG_DEP} )" ) |
2077 |
+ fi |
2078 |
+ done |
2079 |
+ |
2080 |
+ echo "${matches[@]}" |
2081 |
+} |
2082 |
+ |
2083 |
+# @FUNCTION: python_gen_any_dep |
2084 |
+# @USAGE: <dependency-block> [<impl-pattern>...] |
2085 |
+# @DESCRIPTION: |
2086 |
+# Generate an any-of dependency that enforces a version match between |
2087 |
+# the Python interpreter and Python packages. <dependency-block> needs |
2088 |
+# to list one or more dependencies with verbatim '${PYTHON_USEDEP}' |
2089 |
+# references (quoted!) that will get expanded inside the function. |
2090 |
+# Optionally, patterns may be specified to restrict the dependency |
2091 |
+# to a subset of Python implementations supported by the ebuild. |
2092 |
+# |
2093 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2094 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2095 |
+# appropriately all enabled Python 2/3 implementations (alike |
2096 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2097 |
+# to prevent accidental shell filename expansion. |
2098 |
+# |
2099 |
+# This should be used along with an appropriate python_check_deps() |
2100 |
+# that checks which of the any-of blocks were matched, and python_setup |
2101 |
+# call that enables use of the matched implementation. |
2102 |
+# |
2103 |
+# Example use: |
2104 |
+# @CODE |
2105 |
+# DEPEND="$(python_gen_any_dep ' |
2106 |
+# dev-python/foo[${PYTHON_USEDEP}] |
2107 |
+# || ( dev-python/bar[${PYTHON_USEDEP}] |
2108 |
+# dev-python/baz[${PYTHON_USEDEP}] )' -2)" |
2109 |
+# |
2110 |
+# python_check_deps() { |
2111 |
+# has_version "dev-python/foo[${PYTHON_USEDEP}]" \ |
2112 |
+# && { has_version "dev-python/bar[${PYTHON_USEDEP}]" \ |
2113 |
+# || has_version "dev-python/baz[${PYTHON_USEDEP}]"; } |
2114 |
+# } |
2115 |
+# |
2116 |
+# src_compile() { |
2117 |
+# python_foreach_impl usual_code |
2118 |
+# |
2119 |
+# # some common post-build task that requires Python 2 |
2120 |
+# python_setup -2 |
2121 |
+# emake frobnicate |
2122 |
+# } |
2123 |
+# @CODE |
2124 |
+# |
2125 |
+# Example value: |
2126 |
+# @CODE |
2127 |
+# || ( |
2128 |
+# ( |
2129 |
+# dev-lang/python:2.7 |
2130 |
+# dev-python/foo[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] |
2131 |
+# || ( dev-python/bar[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] |
2132 |
+# dev-python/baz[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] ) |
2133 |
+# ) |
2134 |
+# ( |
2135 |
+# dev-lang/python:3.3 |
2136 |
+# dev-python/foo[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] |
2137 |
+# || ( dev-python/bar[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] |
2138 |
+# dev-python/baz[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] ) |
2139 |
+# ) |
2140 |
+# ) |
2141 |
+# @CODE |
2142 |
+python_gen_any_dep() { |
2143 |
+ debug-print-function ${FUNCNAME} "${@}" |
2144 |
+ |
2145 |
+ local depstr=${1} |
2146 |
+ [[ ${depstr} ]] || die "No dependency string provided" |
2147 |
+ shift |
2148 |
+ |
2149 |
+ local i PYTHON_PKG_DEP out= |
2150 |
+ for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2151 |
+ if _python_impl_matches "${i}" "${@}"; then |
2152 |
+ local PYTHON_USEDEP="python_targets_${i}(-),python_single_target_${i}(+)" |
2153 |
+ python_export "${i}" PYTHON_PKG_DEP |
2154 |
+ |
2155 |
+ local i_depstr=${depstr//\$\{PYTHON_USEDEP\}/${PYTHON_USEDEP}} |
2156 |
+ # note: need to strip '=' slot operator for || deps |
2157 |
+ out="( ${PYTHON_PKG_DEP/:0=/:0} ${i_depstr} ) ${out}" |
2158 |
+ fi |
2159 |
+ done |
2160 |
+ echo "|| ( ${out})" |
2161 |
+} |
2162 |
+ |
2163 |
+# @ECLASS-VARIABLE: BUILD_DIR |
2164 |
+# @DESCRIPTION: |
2165 |
+# The current build directory. In global scope, it is supposed to |
2166 |
+# contain an initial build directory; if unset, it defaults to ${S}. |
2167 |
+# |
2168 |
+# In functions run by python_foreach_impl(), the BUILD_DIR is locally |
2169 |
+# set to an implementation-specific build directory. That path is |
2170 |
+# created through appending a hyphen and the implementation name |
2171 |
+# to the final component of the initial BUILD_DIR. |
2172 |
+# |
2173 |
+# Example value: |
2174 |
+# @CODE |
2175 |
+# ${WORKDIR}/foo-1.3-python2_7 |
2176 |
+# @CODE |
2177 |
+ |
2178 |
+# @FUNCTION: python_copy_sources |
2179 |
+# @DESCRIPTION: |
2180 |
+# Create a single copy of the package sources for each enabled Python |
2181 |
+# implementation. |
2182 |
+# |
2183 |
+# The sources are always copied from initial BUILD_DIR (or S if unset) |
2184 |
+# to implementation-specific build directory matching BUILD_DIR used by |
2185 |
+# python_foreach_abi(). |
2186 |
+python_copy_sources() { |
2187 |
+ debug-print-function ${FUNCNAME} "${@}" |
2188 |
+ |
2189 |
+ local MULTIBUILD_VARIANTS |
2190 |
+ _python_obtain_impls |
2191 |
+ |
2192 |
+ multibuild_copy_sources |
2193 |
+} |
2194 |
+ |
2195 |
+# @FUNCTION: _python_obtain_impls |
2196 |
+# @INTERNAL |
2197 |
+# @DESCRIPTION: |
2198 |
+# Set up the enabled implementation list. |
2199 |
+_python_obtain_impls() { |
2200 |
+ _python_validate_useflags |
2201 |
+ |
2202 |
+ if [[ ${PYTHON_COMPAT_OVERRIDE} ]]; then |
2203 |
+ MULTIBUILD_VARIANTS=( ${PYTHON_COMPAT_OVERRIDE} ) |
2204 |
+ return |
2205 |
+ fi |
2206 |
+ |
2207 |
+ MULTIBUILD_VARIANTS=() |
2208 |
+ |
2209 |
+ local impl |
2210 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2211 |
+ has "${impl}" "${PYTHON_COMPAT[@]}" && \ |
2212 |
+ use "python_targets_${impl}" && MULTIBUILD_VARIANTS+=( "${impl}" ) |
2213 |
+ done |
2214 |
+} |
2215 |
+ |
2216 |
+# @FUNCTION: _python_multibuild_wrapper |
2217 |
+# @USAGE: <command> [<args>...] |
2218 |
+# @INTERNAL |
2219 |
+# @DESCRIPTION: |
2220 |
+# Initialize the environment for Python implementation selected |
2221 |
+# for multibuild. |
2222 |
+_python_multibuild_wrapper() { |
2223 |
+ debug-print-function ${FUNCNAME} "${@}" |
2224 |
+ |
2225 |
+ local -x EPYTHON PYTHON |
2226 |
+ local -x PATH=${PATH} PKG_CONFIG_PATH=${PKG_CONFIG_PATH} |
2227 |
+ python_export "${MULTIBUILD_VARIANT}" EPYTHON PYTHON |
2228 |
+ python_wrapper_setup |
2229 |
+ |
2230 |
+ "${@}" |
2231 |
+} |
2232 |
+ |
2233 |
+# @FUNCTION: python_foreach_impl |
2234 |
+# @USAGE: <command> [<args>...] |
2235 |
+# @DESCRIPTION: |
2236 |
+# Run the given command for each of the enabled Python implementations. |
2237 |
+# If additional parameters are passed, they will be passed through |
2238 |
+# to the command. |
2239 |
+# |
2240 |
+# The function will return 0 status if all invocations succeed. |
2241 |
+# Otherwise, the return code from first failing invocation will |
2242 |
+# be returned. |
2243 |
+# |
2244 |
+# For each command being run, EPYTHON, PYTHON and BUILD_DIR are set |
2245 |
+# locally, and the former two are exported to the command environment. |
2246 |
+python_foreach_impl() { |
2247 |
+ debug-print-function ${FUNCNAME} "${@}" |
2248 |
+ |
2249 |
+ local MULTIBUILD_VARIANTS |
2250 |
+ _python_obtain_impls |
2251 |
+ |
2252 |
+ multibuild_foreach_variant _python_multibuild_wrapper "${@}" |
2253 |
+} |
2254 |
+ |
2255 |
+# @FUNCTION: python_setup |
2256 |
+# @USAGE: [<impl-pattern>...] |
2257 |
+# @DESCRIPTION: |
2258 |
+# Find the best (most preferred) Python implementation that is suitable |
2259 |
+# for running common Python code. Set the Python build environment up |
2260 |
+# for that implementation. This function has two modes of operation: |
2261 |
+# pure and any-of dep. |
2262 |
+# |
2263 |
+# The pure mode is used if python_check_deps() function is not declared. |
2264 |
+# In this case, an implementation is considered suitable if it is |
2265 |
+# supported (in PYTHON_COMPAT), enabled (via USE flags) and matches |
2266 |
+# at least one of the patterns passed (or '*' if no patterns passed). |
2267 |
+# |
2268 |
+# Implementation restrictions in the pure mode need to be accompanied |
2269 |
+# by appropriate REQUIRED_USE constraints. Otherwise, the eclass may |
2270 |
+# fail at build time due to unsatisfied dependencies. |
2271 |
+# |
2272 |
+# The any-of dep mode is used if python_check_deps() is declared. |
2273 |
+# In this mode, an implementation is considered suitable if it is |
2274 |
+# supported, matches at least one of the patterns and python_check_deps() |
2275 |
+# has successful return code. USE flags are not considered. |
2276 |
+# |
2277 |
+# The python_check_deps() function in the any-of mode needs to be |
2278 |
+# accompanied by appropriate any-of dependencies. |
2279 |
+# |
2280 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2281 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2282 |
+# appropriately all enabled Python 2/3 implementations (alike |
2283 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2284 |
+# to prevent accidental shell filename expansion. |
2285 |
+# |
2286 |
+# This function needs to be used when Python is being called outside |
2287 |
+# of python_foreach_impl calls (e.g. for shared processes like doc |
2288 |
+# building). python_foreach_impl sets up the build environment itself. |
2289 |
+# |
2290 |
+# Pure mode example: |
2291 |
+# @CODE |
2292 |
+# DEPEND="doc? ( dev-python/epydoc[$(python_gen_usedep 'python2*')] )" |
2293 |
+# REQUIRED_USE="doc? ( $(python_gen_useflags 'python2*') )" |
2294 |
+# |
2295 |
+# src_compile() { |
2296 |
+# #... |
2297 |
+# if use doc; then |
2298 |
+# python_setup 'python2*' |
2299 |
+# make doc |
2300 |
+# fi |
2301 |
+# } |
2302 |
+# @CODE |
2303 |
+# |
2304 |
+# Any-of mode example: |
2305 |
+# @CODE |
2306 |
+# DEPEND="doc? ( |
2307 |
+# $(python_gen_any_dep 'dev-python/epydoc[${PYTHON_USEDEP}]' 'python2*') )" |
2308 |
+# |
2309 |
+# python_check_deps() { |
2310 |
+# has_version "dev-python/epydoc[${PYTHON_USEDEP}]" |
2311 |
+# } |
2312 |
+# |
2313 |
+# src_compile() { |
2314 |
+# #... |
2315 |
+# if use doc; then |
2316 |
+# python_setup 'python2*' |
2317 |
+# make doc |
2318 |
+# fi |
2319 |
+# } |
2320 |
+# @CODE |
2321 |
+python_setup() { |
2322 |
+ debug-print-function ${FUNCNAME} "${@}" |
2323 |
+ |
2324 |
+ _python_validate_useflags |
2325 |
+ local pycompat=( "${PYTHON_COMPAT[@]}" ) |
2326 |
+ if [[ ${PYTHON_COMPAT_OVERRIDE} ]]; then |
2327 |
+ pycompat=( ${PYTHON_COMPAT_OVERRIDE} ) |
2328 |
+ fi |
2329 |
+ |
2330 |
+ local has_check_deps |
2331 |
+ declare -f python_check_deps >/dev/null && has_check_deps=1 |
2332 |
+ |
2333 |
+ # (reverse iteration -- newest impl first) |
2334 |
+ local found |
2335 |
+ for (( i = ${#_PYTHON_SUPPORTED_IMPLS[@]} - 1; i >= 0; i-- )); do |
2336 |
+ local impl=${_PYTHON_SUPPORTED_IMPLS[i]} |
2337 |
+ |
2338 |
+ # check PYTHON_COMPAT[_OVERRIDE] |
2339 |
+ has "${impl}" "${pycompat[@]}" || continue |
2340 |
+ |
2341 |
+ # match USE flags only if override is not in effect |
2342 |
+ # and python_check_deps() is not defined |
2343 |
+ if [[ ! ${PYTHON_COMPAT_OVERRIDE} && ! ${has_check_deps} ]]; then |
2344 |
+ use "python_targets_${impl}" || continue |
2345 |
+ fi |
2346 |
+ |
2347 |
+ # check patterns |
2348 |
+ _python_impl_matches "${impl}" "${@}" || continue |
2349 |
+ |
2350 |
+ python_export "${impl}" EPYTHON PYTHON |
2351 |
+ |
2352 |
+ # if python_check_deps() is declared, switch into any-of mode |
2353 |
+ if [[ ${has_check_deps} ]]; then |
2354 |
+ # first check if the interpreter is installed |
2355 |
+ python_is_installed "${impl}" || continue |
2356 |
+ # then run python_check_deps |
2357 |
+ local PYTHON_USEDEP="python_targets_${impl}(-),python_single_target_${impl}(+)" |
2358 |
+ python_check_deps || continue |
2359 |
+ fi |
2360 |
+ |
2361 |
+ found=1 |
2362 |
+ break |
2363 |
+ done |
2364 |
+ |
2365 |
+ if [[ ! ${found} ]]; then |
2366 |
+ eerror "${FUNCNAME}: none of the enabled implementation matched the patterns." |
2367 |
+ eerror " patterns: ${@-'(*)'}" |
2368 |
+ eerror "Likely a REQUIRED_USE constraint (possibly USE-conditional) is missing." |
2369 |
+ eerror " suggested: || ( \$(python_gen_useflags ${@}) )" |
2370 |
+ eerror "(remember to quote all the patterns with '')" |
2371 |
+ die "${FUNCNAME}: no enabled implementation satisfy requirements" |
2372 |
+ fi |
2373 |
+ |
2374 |
+ python_wrapper_setup |
2375 |
+} |
2376 |
+ |
2377 |
+# @FUNCTION: python_replicate_script |
2378 |
+# @USAGE: <path>... |
2379 |
+# @DESCRIPTION: |
2380 |
+# Copy the given script to variants for all enabled Python |
2381 |
+# implementations, then replace it with a symlink to the wrapper. |
2382 |
+# |
2383 |
+# All specified files must start with a 'python' shebang. A file not |
2384 |
+# having a matching shebang will be refused. |
2385 |
+python_replicate_script() { |
2386 |
+ debug-print-function ${FUNCNAME} "${@}" |
2387 |
+ |
2388 |
+ _python_replicate_script() { |
2389 |
+ local _PYTHON_FIX_SHEBANG_QUIET=1 |
2390 |
+ |
2391 |
+ local PYTHON_SCRIPTDIR |
2392 |
+ python_export PYTHON_SCRIPTDIR |
2393 |
+ |
2394 |
+ ( |
2395 |
+ exeopts -m 0755 |
2396 |
+ exeinto "${PYTHON_SCRIPTDIR#${EPREFIX}}" |
2397 |
+ doexe "${files[@]}" |
2398 |
+ ) |
2399 |
+ |
2400 |
+ python_fix_shebang -q \ |
2401 |
+ "${files[@]/*\//${D%/}/${PYTHON_SCRIPTDIR}/}" |
2402 |
+ } |
2403 |
+ |
2404 |
+ local files=( "${@}" ) |
2405 |
+ python_foreach_impl _python_replicate_script |
2406 |
+ unset -f _python_replicate_script |
2407 |
+ |
2408 |
+ # install the wrappers |
2409 |
+ local f |
2410 |
+ for f; do |
2411 |
+ _python_ln_rel "${ED%/}/usr/lib/python-exec/python-exec2" "${f}" || die |
2412 |
+ done |
2413 |
+} |
2414 |
+ |
2415 |
+_PYTHON_R2=1 |
2416 |
+fi |
2417 |
diff --git a/eclass/python-single-r2.eclass b/eclass/python-single-r2.eclass |
2418 |
new file mode 100644 |
2419 |
index 000000000000..5bf6ea7221bc |
2420 |
--- /dev/null |
2421 |
+++ b/eclass/python-single-r2.eclass |
2422 |
@@ -0,0 +1,507 @@ |
2423 |
+# Copyright 1999-2020 Gentoo Authors |
2424 |
+# Distributed under the terms of the GNU General Public License v2 |
2425 |
+ |
2426 |
+# @ECLASS: python-single-r2.eclass |
2427 |
+# @MAINTAINER: |
2428 |
+# Python team <python@g.o> |
2429 |
+# @AUTHOR: |
2430 |
+# Author: Michał Górny <mgorny@g.o> |
2431 |
+# @SUPPORTED_EAPIS: 5 6 7 |
2432 |
+# @BLURB: An eclass for Python packages not installed for multiple implementations. |
2433 |
+# @DESCRIPTION: |
2434 |
+# An extension of the python-r2 eclass suite for packages which |
2435 |
+# don't support being installed for multiple Python implementations. |
2436 |
+# This mostly includes tools embedding Python and packages using foreign |
2437 |
+# build systems. |
2438 |
+# |
2439 |
+# This eclass sets correct IUSE. It also provides PYTHON_DEPS |
2440 |
+# and PYTHON_REQUIRED_USE that need to be added to appropriate ebuild |
2441 |
+# metadata variables. |
2442 |
+# |
2443 |
+# The eclass exports PYTHON_SINGLE_USEDEP that is suitable for depending |
2444 |
+# on other packages using the eclass. Dependencies on packages using |
2445 |
+# python-r2 should be created via python_gen_cond_dep() function, |
2446 |
+# using PYTHON_MULTI_USEDEP placeholder. |
2447 |
+# |
2448 |
+# Please note that packages support multiple Python implementations |
2449 |
+# (using python-r2 eclass) can not depend on packages not supporting |
2450 |
+# them (using this eclass). |
2451 |
+# |
2452 |
+# Please note that python-single-r2 will always inherit python-utils-r2 |
2453 |
+# as well. Thus, all the functions defined there can be used |
2454 |
+# in the packages using python-single-r2, and there is no need ever |
2455 |
+# to inherit both. |
2456 |
+ |
2457 |
+case "${EAPI:-0}" in |
2458 |
+ 0|1|2|3|4) |
2459 |
+ die "Unsupported EAPI=${EAPI:-0} (too old) for ${ECLASS}" |
2460 |
+ ;; |
2461 |
+ 5|6|7) |
2462 |
+ # EAPI=5 is required for sane USE_EXPAND dependencies |
2463 |
+ ;; |
2464 |
+ *) |
2465 |
+ die "Unsupported EAPI=${EAPI} (unknown) for ${ECLASS}" |
2466 |
+ ;; |
2467 |
+esac |
2468 |
+ |
2469 |
+if [[ ! ${_PYTHON_SINGLE_R2} ]]; then |
2470 |
+ |
2471 |
+if [[ ${_PYTHON_R2} ]]; then |
2472 |
+ die 'python-single-r2.eclass can not be used with python-r2.eclass.' |
2473 |
+elif [[ ${_PYTHON_ANY_R2} ]]; then |
2474 |
+ die 'python-single-r2.eclass can not be used with python-any-r2.eclass.' |
2475 |
+fi |
2476 |
+ |
2477 |
+inherit python-utils-r2 |
2478 |
+ |
2479 |
+fi |
2480 |
+ |
2481 |
+EXPORT_FUNCTIONS pkg_setup |
2482 |
+ |
2483 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT |
2484 |
+# @REQUIRED |
2485 |
+# @DESCRIPTION: |
2486 |
+# This variable contains a list of Python implementations the package |
2487 |
+# supports. It must be set before the `inherit' call. It has to be |
2488 |
+# an array. |
2489 |
+# |
2490 |
+# Example: |
2491 |
+# @CODE |
2492 |
+# PYTHON_COMPAT=( python2_7 python3_3 python3_4 ) |
2493 |
+# @CODE |
2494 |
+# |
2495 |
+# Please note that you can also use bash brace expansion if you like: |
2496 |
+# @CODE |
2497 |
+# PYTHON_COMPAT=( python2_7 python3_{3,4} ) |
2498 |
+# @CODE |
2499 |
+ |
2500 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT_OVERRIDE |
2501 |
+# @INTERNAL |
2502 |
+# @DESCRIPTION: |
2503 |
+# This variable can be used when working with ebuilds to override |
2504 |
+# the in-ebuild PYTHON_COMPAT. It is a string naming the implementation |
2505 |
+# which package will be built for. It needs to be specified |
2506 |
+# in the calling environment, and not in ebuilds. |
2507 |
+# |
2508 |
+# It should be noted that in order to preserve metadata immutability, |
2509 |
+# PYTHON_COMPAT_OVERRIDE does not affect IUSE nor dependencies. |
2510 |
+# The state of PYTHON_SINGLE_TARGET is ignored, and the implementation |
2511 |
+# in PYTHON_COMPAT_OVERRIDE is built instead. Dependencies need to be |
2512 |
+# satisfied manually. |
2513 |
+# |
2514 |
+# Example: |
2515 |
+# @CODE |
2516 |
+# PYTHON_COMPAT_OVERRIDE='pypy' emerge -1v dev-python/bar |
2517 |
+# @CODE |
2518 |
+ |
2519 |
+# @ECLASS-VARIABLE: PYTHON_REQ_USE |
2520 |
+# @DEFAULT_UNSET |
2521 |
+# @DESCRIPTION: |
2522 |
+# The list of USEflags required to be enabled on the chosen Python |
2523 |
+# implementations, formed as a USE-dependency string. It should be valid |
2524 |
+# for all implementations in PYTHON_COMPAT, so it may be necessary to |
2525 |
+# use USE defaults. |
2526 |
+# |
2527 |
+# This should be set before calling `inherit'. |
2528 |
+# |
2529 |
+# Example: |
2530 |
+# @CODE |
2531 |
+# PYTHON_REQ_USE="gdbm,ncurses(-)?" |
2532 |
+# @CODE |
2533 |
+# |
2534 |
+# It will cause the Python dependencies to look like: |
2535 |
+# @CODE |
2536 |
+# python_single_target_pythonX_Y? ( dev-lang/python:X.Y[gdbm,ncurses(-)?] ) |
2537 |
+# @CODE |
2538 |
+ |
2539 |
+# @ECLASS-VARIABLE: PYTHON_DEPS |
2540 |
+# @DESCRIPTION: |
2541 |
+# This is an eclass-generated Python dependency string for all |
2542 |
+# implementations listed in PYTHON_COMPAT. |
2543 |
+# |
2544 |
+# The dependency string is conditional on PYTHON_SINGLE_TARGET. |
2545 |
+# |
2546 |
+# Example use: |
2547 |
+# @CODE |
2548 |
+# RDEPEND="${PYTHON_DEPS} |
2549 |
+# dev-foo/mydep" |
2550 |
+# DEPEND="${RDEPEND}" |
2551 |
+# @CODE |
2552 |
+# |
2553 |
+# Example value: |
2554 |
+# @CODE |
2555 |
+# dev-lang/python-exec:= |
2556 |
+# python_single_target_python2_7? ( dev-lang/python:2.7[gdbm] ) |
2557 |
+# python_single_target_pypy? ( dev-python/pypy[gdbm] ) |
2558 |
+# @CODE |
2559 |
+ |
2560 |
+# @ECLASS-VARIABLE: PYTHON_SINGLE_USEDEP |
2561 |
+# @DESCRIPTION: |
2562 |
+# This is an eclass-generated USE-dependency string which can be used to |
2563 |
+# depend on another python-single-r2 package being built for the same |
2564 |
+# Python implementations. |
2565 |
+# |
2566 |
+# If you need to depend on a multi-impl (python-r2) package, use |
2567 |
+# python_gen_cond_dep with PYTHON_MULTI_USEDEP placeholder instead. |
2568 |
+# |
2569 |
+# Example use: |
2570 |
+# @CODE |
2571 |
+# RDEPEND="dev-python/foo[${PYTHON_SINGLE_USEDEP}]" |
2572 |
+# @CODE |
2573 |
+# |
2574 |
+# Example value: |
2575 |
+# @CODE |
2576 |
+# python_single_target_python3_4(-)? |
2577 |
+# @CODE |
2578 |
+ |
2579 |
+# @ECLASS-VARIABLE: PYTHON_MULTI_USEDEP |
2580 |
+# @DESCRIPTION: |
2581 |
+# This is a placeholder variable supported by python_gen_cond_dep, |
2582 |
+# in order to depend on python-r2 packages built for the same Python |
2583 |
+# implementations. |
2584 |
+# |
2585 |
+# Example use: |
2586 |
+# @CODE |
2587 |
+# RDEPEND="$(python_gen_cond_dep ' |
2588 |
+# dev-python/foo[${PYTHON_MULTI_USEDEP}] |
2589 |
+# ')" |
2590 |
+# @CODE |
2591 |
+# |
2592 |
+# Example value: |
2593 |
+# @CODE |
2594 |
+# python_targets_python3_4(-) |
2595 |
+# @CODE |
2596 |
+ |
2597 |
+# @ECLASS-VARIABLE: PYTHON_REQUIRED_USE |
2598 |
+# @DESCRIPTION: |
2599 |
+# This is an eclass-generated required-use expression which ensures |
2600 |
+# that exactly one PYTHON_SINGLE_TARGET value has been enabled. |
2601 |
+# |
2602 |
+# This expression should be utilized in an ebuild by including it in |
2603 |
+# REQUIRED_USE, optionally behind a use flag. |
2604 |
+# |
2605 |
+# Example use: |
2606 |
+# @CODE |
2607 |
+# REQUIRED_USE="python? ( ${PYTHON_REQUIRED_USE} )" |
2608 |
+# @CODE |
2609 |
+# |
2610 |
+# Example value: |
2611 |
+# @CODE |
2612 |
+# ^^ ( python_single_target_python2_7 python_single_target_python3_3 ) |
2613 |
+# @CODE |
2614 |
+ |
2615 |
+_python_single_set_globals() { |
2616 |
+ _python_set_impls |
2617 |
+ |
2618 |
+ local flags=( "${_PYTHON_SUPPORTED_IMPLS[@]/#/python_single_target_}" ) |
2619 |
+ |
2620 |
+ if [[ ${#_PYTHON_SUPPORTED_IMPLS[@]} -eq 1 ]]; then |
2621 |
+ # if only one implementation is supported, use IUSE defaults |
2622 |
+ # to avoid requesting the user to enable it |
2623 |
+ IUSE="+${flags[0]}" |
2624 |
+ else |
2625 |
+ IUSE="${flags[*]}" |
2626 |
+ fi |
2627 |
+ |
2628 |
+ local requse="^^ ( ${flags[*]} )" |
2629 |
+ local single_flags="${flags[@]/%/(-)?}" |
2630 |
+ local single_usedep=${single_flags// /,} |
2631 |
+ |
2632 |
+ local deps= i PYTHON_PKG_DEP |
2633 |
+ for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2634 |
+ python_export "${i}" PYTHON_PKG_DEP |
2635 |
+ # 1) well, python-exec would suffice as an RDEP |
2636 |
+ # but no point in making this overcomplex, BDEP doesn't hurt anyone |
2637 |
+ # 2) python-exec should be built with all targets forced anyway |
2638 |
+ # but if new targets were added, we may need to force a rebuild |
2639 |
+ deps+="python_single_target_${i}? ( |
2640 |
+ ${PYTHON_PKG_DEP} |
2641 |
+ >=dev-lang/python-exec-2:=[python_targets_${i}] |
2642 |
+ ) " |
2643 |
+ done |
2644 |
+ |
2645 |
+ if [[ ${PYTHON_DEPS+1} ]]; then |
2646 |
+ if [[ ${PYTHON_DEPS} != "${deps}" ]]; then |
2647 |
+ eerror "PYTHON_DEPS have changed between inherits (PYTHON_REQ_USE?)!" |
2648 |
+ eerror "Before: ${PYTHON_DEPS}" |
2649 |
+ eerror "Now : ${deps}" |
2650 |
+ die "PYTHON_DEPS integrity check failed" |
2651 |
+ fi |
2652 |
+ |
2653 |
+ # these two are formality -- they depend on PYTHON_COMPAT only |
2654 |
+ if [[ ${PYTHON_REQUIRED_USE} != ${requse} ]]; then |
2655 |
+ eerror "PYTHON_REQUIRED_USE have changed between inherits!" |
2656 |
+ eerror "Before: ${PYTHON_REQUIRED_USE}" |
2657 |
+ eerror "Now : ${requse}" |
2658 |
+ die "PYTHON_REQUIRED_USE integrity check failed" |
2659 |
+ fi |
2660 |
+ |
2661 |
+ if [[ ${PYTHON_SINGLE_USEDEP} != "${single_usedep}" ]]; then |
2662 |
+ eerror "PYTHON_SINGLE_USEDEP have changed between inherits!" |
2663 |
+ eerror "Before: ${PYTHON_SINGLE_USEDEP}" |
2664 |
+ eerror "Now : ${single_usedep}" |
2665 |
+ die "PYTHON_SINGLE_USEDEP integrity check failed" |
2666 |
+ fi |
2667 |
+ else |
2668 |
+ PYTHON_DEPS=${deps} |
2669 |
+ PYTHON_REQUIRED_USE=${requse} |
2670 |
+ PYTHON_USEDEP='%PYTHON_USEDEP-HAS-BEEN-REMOVED%' |
2671 |
+ PYTHON_SINGLE_USEDEP=${single_usedep} |
2672 |
+ readonly PYTHON_DEPS PYTHON_REQUIRED_USE PYTHON_SINGLE_USEDEP \ |
2673 |
+ PYTHON_USEDEP |
2674 |
+ fi |
2675 |
+} |
2676 |
+_python_single_set_globals |
2677 |
+unset -f _python_single_set_globals |
2678 |
+ |
2679 |
+if [[ ! ${_PYTHON_SINGLE_R2} ]]; then |
2680 |
+ |
2681 |
+# @FUNCTION: _python_gen_usedep |
2682 |
+# @INTERNAL |
2683 |
+# @USAGE: [<pattern>...] |
2684 |
+# @DESCRIPTION: |
2685 |
+# Output a USE dependency string for Python implementations which |
2686 |
+# are both in PYTHON_COMPAT and match any of the patterns passed |
2687 |
+# as parameters to the function. |
2688 |
+# |
2689 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2690 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2691 |
+# appropriately all enabled Python 2/3 implementations (alike |
2692 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2693 |
+# to prevent accidental shell filename expansion. |
2694 |
+# |
2695 |
+# This is an internal function used to implement python_gen_cond_dep. |
2696 |
+_python_gen_usedep() { |
2697 |
+ debug-print-function ${FUNCNAME} "${@}" |
2698 |
+ |
2699 |
+ local impl matches=() |
2700 |
+ |
2701 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2702 |
+ if _python_impl_matches "${impl}" "${@}"; then |
2703 |
+ matches+=( |
2704 |
+ "python_single_target_${impl}(-)?" |
2705 |
+ ) |
2706 |
+ fi |
2707 |
+ done |
2708 |
+ |
2709 |
+ [[ ${matches[@]} ]] || die "No supported implementations match python_gen_usedep patterns: ${@}" |
2710 |
+ |
2711 |
+ local out=${matches[@]} |
2712 |
+ echo "${out// /,}" |
2713 |
+} |
2714 |
+ |
2715 |
+# @FUNCTION: python_gen_useflags |
2716 |
+# @USAGE: [<pattern>...] |
2717 |
+# @DESCRIPTION: |
2718 |
+# Output a list of USE flags for Python implementations which |
2719 |
+# are both in PYTHON_COMPAT and match any of the patterns passed |
2720 |
+# as parameters to the function. |
2721 |
+# |
2722 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2723 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2724 |
+# appropriately all enabled Python 2/3 implementations (alike |
2725 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2726 |
+# to prevent accidental shell filename expansion. |
2727 |
+# |
2728 |
+# Example: |
2729 |
+# @CODE |
2730 |
+# PYTHON_COMPAT=( python{2_7,3_4} ) |
2731 |
+# REQUIRED_USE="doc? ( ^^ ( $(python_gen_useflags 'python2*') ) )" |
2732 |
+# @CODE |
2733 |
+# |
2734 |
+# It will cause the variable to look like: |
2735 |
+# @CODE |
2736 |
+# REQUIRED_USE="doc? ( ^^ ( python_single_target_python2_7 ) )" |
2737 |
+# @CODE |
2738 |
+python_gen_useflags() { |
2739 |
+ debug-print-function ${FUNCNAME} "${@}" |
2740 |
+ |
2741 |
+ local impl matches=() |
2742 |
+ |
2743 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2744 |
+ if _python_impl_matches "${impl}" "${@}"; then |
2745 |
+ matches+=( "python_single_target_${impl}" ) |
2746 |
+ fi |
2747 |
+ done |
2748 |
+ |
2749 |
+ echo "${matches[@]}" |
2750 |
+} |
2751 |
+ |
2752 |
+# @FUNCTION: python_gen_cond_dep |
2753 |
+# @USAGE: <dependency> [<pattern>...] |
2754 |
+# @DESCRIPTION: |
2755 |
+# Output a list of <dependency>-ies made conditional to USE flags |
2756 |
+# of Python implementations which are both in PYTHON_COMPAT and match |
2757 |
+# any of the patterns passed as the remaining parameters. |
2758 |
+# |
2759 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2760 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2761 |
+# appropriately all enabled Python 2/3 implementations (alike |
2762 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2763 |
+# to prevent accidental shell filename expansion. |
2764 |
+# |
2765 |
+# In order to enforce USE constraints on the packages, verbatim |
2766 |
+# '${PYTHON_SINGLE_USEDEP}' and '${PYTHON_MULTI_USEDEP}' (quoted!) may |
2767 |
+# be placed in the dependency specification. It will get expanded within |
2768 |
+# the function into a proper USE dependency string. |
2769 |
+# |
2770 |
+# Example: |
2771 |
+# @CODE |
2772 |
+# PYTHON_COMPAT=( python{2_7,3_{3,4}} pypy ) |
2773 |
+# RDEPEND="$(python_gen_cond_dep \ |
2774 |
+# 'dev-python/unittest2[${PYTHON_MULTI_USEDEP}]' python2_7 pypy )" |
2775 |
+# @CODE |
2776 |
+# |
2777 |
+# It will cause the variable to look like: |
2778 |
+# @CODE |
2779 |
+# RDEPEND="python_single_target_python2_7? ( |
2780 |
+# dev-python/unittest2[python_targets_python2_7(-)?,...] ) |
2781 |
+# python_single_target_pypy? ( |
2782 |
+# dev-python/unittest2[python_targets_pypy(-)?,...] )" |
2783 |
+# @CODE |
2784 |
+python_gen_cond_dep() { |
2785 |
+ debug-print-function ${FUNCNAME} "${@}" |
2786 |
+ |
2787 |
+ local impl matches=() |
2788 |
+ |
2789 |
+ local dep=${1} |
2790 |
+ shift |
2791 |
+ |
2792 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2793 |
+ if _python_impl_matches "${impl}" "${@}"; then |
2794 |
+ # substitute ${PYTHON_SINGLE_USEDEP} if used |
2795 |
+ # (since python_gen_usedep() will not return |
2796 |
+ # ${PYTHON_SINGLE_USEDEP}, the code is run at most once) |
2797 |
+ if [[ ${dep} == *'${PYTHON_SINGLE_USEDEP}'* ]]; then |
2798 |
+ local usedep=$(_python_gen_usedep "${@}") |
2799 |
+ dep=${dep//\$\{PYTHON_SINGLE_USEDEP\}/${usedep}} |
2800 |
+ fi |
2801 |
+ local multi_usedep="python_targets_${impl}(-)" |
2802 |
+ |
2803 |
+ matches+=( "python_single_target_${impl}? ( |
2804 |
+ ${dep//\$\{PYTHON_MULTI_USEDEP\}/${multi_usedep}} )" ) |
2805 |
+ fi |
2806 |
+ done |
2807 |
+ |
2808 |
+ echo "${matches[@]}" |
2809 |
+} |
2810 |
+ |
2811 |
+# @FUNCTION: python_gen_impl_dep |
2812 |
+# @USAGE: [<requested-use-flags> [<impl-pattern>...]] |
2813 |
+# @DESCRIPTION: |
2814 |
+# Output a dependency on Python implementations with the specified USE |
2815 |
+# dependency string appended, or no USE dependency string if called |
2816 |
+# without the argument (or with empty argument). If any implementation |
2817 |
+# patterns are passed, the output dependencies will be generated only |
2818 |
+# for the implementations matching them. |
2819 |
+# |
2820 |
+# The patterns can be either fnmatch-style patterns (matched via bash |
2821 |
+# == operator against PYTHON_COMPAT values) or '-2' / '-3' to indicate |
2822 |
+# appropriately all enabled Python 2/3 implementations (alike |
2823 |
+# python_is_python3). Remember to escape or quote the fnmatch patterns |
2824 |
+# to prevent accidental shell filename expansion. |
2825 |
+# |
2826 |
+# Use this function when you need to request different USE flags |
2827 |
+# on the Python interpreter depending on package's USE flags. If you |
2828 |
+# only need a single set of interpreter USE flags, just set |
2829 |
+# PYTHON_REQ_USE and use ${PYTHON_DEPS} globally. |
2830 |
+# |
2831 |
+# Example: |
2832 |
+# @CODE |
2833 |
+# PYTHON_COMPAT=( python{2_7,3_{3,4}} pypy ) |
2834 |
+# RDEPEND="foo? ( $(python_gen_impl_dep 'xml(+)') )" |
2835 |
+# @CODE |
2836 |
+# |
2837 |
+# It will cause the variable to look like: |
2838 |
+# @CODE |
2839 |
+# RDEPEND="foo? ( |
2840 |
+# python_single_target_python2_7? ( |
2841 |
+# dev-lang/python:2.7[xml(+)] ) |
2842 |
+# python_single_target_pypy? ( |
2843 |
+# dev-python/pypy[xml(+)] ) )" |
2844 |
+# @CODE |
2845 |
+python_gen_impl_dep() { |
2846 |
+ debug-print-function ${FUNCNAME} "${@}" |
2847 |
+ |
2848 |
+ local impl |
2849 |
+ local matches=() |
2850 |
+ |
2851 |
+ local PYTHON_REQ_USE=${1} |
2852 |
+ shift |
2853 |
+ |
2854 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2855 |
+ if _python_impl_matches "${impl}" "${@}"; then |
2856 |
+ local PYTHON_PKG_DEP |
2857 |
+ python_export "${impl}" PYTHON_PKG_DEP |
2858 |
+ matches+=( "python_single_target_${impl}? ( ${PYTHON_PKG_DEP} )" ) |
2859 |
+ fi |
2860 |
+ done |
2861 |
+ |
2862 |
+ echo "${matches[@]}" |
2863 |
+} |
2864 |
+ |
2865 |
+# @FUNCTION: python_setup |
2866 |
+# @DESCRIPTION: |
2867 |
+# Determine what the selected Python implementation is and set |
2868 |
+# the Python build environment up for it. |
2869 |
+python_setup() { |
2870 |
+ debug-print-function ${FUNCNAME} "${@}" |
2871 |
+ |
2872 |
+ unset EPYTHON |
2873 |
+ |
2874 |
+ # support developer override |
2875 |
+ if [[ ${PYTHON_COMPAT_OVERRIDE} ]]; then |
2876 |
+ local impls=( ${PYTHON_COMPAT_OVERRIDE} ) |
2877 |
+ [[ ${#impls[@]} -eq 1 ]] || die "PYTHON_COMPAT_OVERRIDE must name exactly one implementation for python-single-r2" |
2878 |
+ |
2879 |
+ ewarn "WARNING: PYTHON_COMPAT_OVERRIDE in effect. The following Python" |
2880 |
+ ewarn "implementation will be used:" |
2881 |
+ ewarn |
2882 |
+ ewarn " ${PYTHON_COMPAT_OVERRIDE}" |
2883 |
+ ewarn |
2884 |
+ ewarn "Dependencies won't be satisfied, and PYTHON_SINGLE_TARGET flags will be ignored." |
2885 |
+ |
2886 |
+ python_export "${impls[0]}" EPYTHON PYTHON |
2887 |
+ python_wrapper_setup |
2888 |
+ return |
2889 |
+ fi |
2890 |
+ |
2891 |
+ local impl |
2892 |
+ for impl in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do |
2893 |
+ if use "python_single_target_${impl}"; then |
2894 |
+ if [[ ${EPYTHON} ]]; then |
2895 |
+ eerror "Your PYTHON_SINGLE_TARGET setting lists more than a single Python" |
2896 |
+ eerror "implementation. Please set it to just one value. If you need" |
2897 |
+ eerror "to override the value for a single package, please use package.env" |
2898 |
+ eerror "or an equivalent solution (man 5 portage)." |
2899 |
+ echo |
2900 |
+ die "More than one implementation in PYTHON_SINGLE_TARGET." |
2901 |
+ fi |
2902 |
+ |
2903 |
+ python_export "${impl}" EPYTHON PYTHON |
2904 |
+ python_wrapper_setup |
2905 |
+ fi |
2906 |
+ done |
2907 |
+ |
2908 |
+ if [[ ! ${EPYTHON} ]]; then |
2909 |
+ eerror "No Python implementation selected for the build. Please set" |
2910 |
+ eerror "the PYTHON_SINGLE_TARGET variable in your make.conf to one" |
2911 |
+ eerror "of the following values:" |
2912 |
+ eerror |
2913 |
+ eerror "${_PYTHON_SUPPORTED_IMPLS[@]}" |
2914 |
+ echo |
2915 |
+ die "No supported Python implementation in PYTHON_SINGLE_TARGET." |
2916 |
+ fi |
2917 |
+} |
2918 |
+ |
2919 |
+# @FUNCTION: python-single-r2_pkg_setup |
2920 |
+# @DESCRIPTION: |
2921 |
+# Runs python_setup. |
2922 |
+python-single-r2_pkg_setup() { |
2923 |
+ debug-print-function ${FUNCNAME} "${@}" |
2924 |
+ |
2925 |
+ [[ ${MERGE_TYPE} != binary ]] && python_setup |
2926 |
+} |
2927 |
+ |
2928 |
+_PYTHON_SINGLE_R2=1 |
2929 |
+fi |
2930 |
diff --git a/eclass/python-utils-r2.eclass b/eclass/python-utils-r2.eclass |
2931 |
new file mode 100644 |
2932 |
index 000000000000..9821c043021a |
2933 |
--- /dev/null |
2934 |
+++ b/eclass/python-utils-r2.eclass |
2935 |
@@ -0,0 +1,1518 @@ |
2936 |
+# Copyright 1999-2020 Gentoo Authors |
2937 |
+# Distributed under the terms of the GNU General Public License v2 |
2938 |
+ |
2939 |
+# @ECLASS: python-utils-r2.eclass |
2940 |
+# @MAINTAINER: |
2941 |
+# Python team <python@g.o> |
2942 |
+# @AUTHOR: |
2943 |
+# Author: Michał Górny <mgorny@g.o> |
2944 |
+# @SUPPORTED_EAPIS: 5 6 7 |
2945 |
+# @BLURB: Utility functions for packages with Python parts. |
2946 |
+# @DESCRIPTION: |
2947 |
+# A utility eclass providing functions to query Python implementations, |
2948 |
+# install Python modules and scripts. |
2949 |
+# |
2950 |
+# This eclass does not set any metadata variables nor export any phase |
2951 |
+# functions. It can be inherited safely. |
2952 |
+ |
2953 |
+case "${EAPI:-0}" in |
2954 |
+ [0-4]) die "Unsupported EAPI=${EAPI:-0} (too old) for ${ECLASS}" ;; |
2955 |
+ [5-7]) ;; |
2956 |
+ *) die "Unsupported EAPI=${EAPI} (unknown) for ${ECLASS}" ;; |
2957 |
+esac |
2958 |
+ |
2959 |
+if [[ ${_PYTHON_UTILS_R1} ]]; then |
2960 |
+ die 'python-r2 suite eclasses can not be combined with python-r1 suite.' |
2961 |
+fi |
2962 |
+ |
2963 |
+if [[ ! ${_PYTHON_UTILS_R2} ]]; then |
2964 |
+ |
2965 |
+[[ ${EAPI} == 5 ]] && inherit eutils multilib |
2966 |
+inherit toolchain-funcs |
2967 |
+ |
2968 |
+# @ECLASS-VARIABLE: _PYTHON_ALL_IMPLS |
2969 |
+# @INTERNAL |
2970 |
+# @DESCRIPTION: |
2971 |
+# All supported Python implementations, most preferred last. |
2972 |
+_PYTHON_ALL_IMPLS=( |
2973 |
+ pypy3 |
2974 |
+ python2_7 |
2975 |
+ python3_6 python3_7 python3_8 |
2976 |
+) |
2977 |
+readonly _PYTHON_ALL_IMPLS |
2978 |
+ |
2979 |
+# @ECLASS-VARIABLE: PYTHON_COMPAT_NO_STRICT |
2980 |
+# @INTERNAL |
2981 |
+# @DESCRIPTION: |
2982 |
+# Set to a non-empty value in order to make eclass tolerate (ignore) |
2983 |
+# unknown implementations in PYTHON_COMPAT. |
2984 |
+# |
2985 |
+# This is intended to be set by the user when using ebuilds that may |
2986 |
+# have unknown (newer) implementations in PYTHON_COMPAT. The assumption |
2987 |
+# is that the ebuilds are intended to be used within multiple contexts |
2988 |
+# which can involve revisions of this eclass that support a different |
2989 |
+# set of Python implementations. |
2990 |
+ |
2991 |
+# @FUNCTION: _python_impl_supported |
2992 |
+# @USAGE: <impl> |
2993 |
+# @INTERNAL |
2994 |
+# @DESCRIPTION: |
2995 |
+# Check whether the implementation <impl> (PYTHON_COMPAT-form) |
2996 |
+# is still supported. |
2997 |
+# |
2998 |
+# Returns 0 if the implementation is valid and supported. If it is |
2999 |
+# unsupported, returns 1 -- and the caller should ignore the entry. |
3000 |
+# If it is invalid, dies with an appopriate error messages. |
3001 |
+_python_impl_supported() { |
3002 |
+ debug-print-function ${FUNCNAME} "${@}" |
3003 |
+ |
3004 |
+ [[ ${#} -eq 1 ]] || die "${FUNCNAME}: takes exactly 1 argument (impl)." |
3005 |
+ |
3006 |
+ local impl=${1} |
3007 |
+ |
3008 |
+ # keep in sync with _PYTHON_ALL_IMPLS! |
3009 |
+ # (not using that list because inline patterns shall be faster) |
3010 |
+ case "${impl}" in |
3011 |
+ python2_7|python3_[678]|pypy3) |
3012 |
+ return 0 |
3013 |
+ ;; |
3014 |
+ jython2_7|pypy|pypy1_[89]|pypy2_0|python2_[56]|python3_[12345]) |
3015 |
+ return 1 |
3016 |
+ ;; |
3017 |
+ *) |
3018 |
+ [[ ${PYTHON_COMPAT_NO_STRICT} ]] && return 1 |
3019 |
+ die "Invalid implementation in PYTHON_COMPAT: ${impl}" |
3020 |
+ esac |
3021 |
+} |
3022 |
+ |
3023 |
+# @FUNCTION: _python_set_impls |
3024 |
+# @INTERNAL |
3025 |
+# @DESCRIPTION: |
3026 |
+# Check PYTHON_COMPAT for well-formedness and validity, then set |
3027 |
+# two global variables: |
3028 |
+# |
3029 |
+# - _PYTHON_SUPPORTED_IMPLS containing valid implementations supported |
3030 |
+# by the ebuild (PYTHON_COMPAT - dead implementations), |
3031 |
+# |
3032 |
+# - and _PYTHON_UNSUPPORTED_IMPLS containing valid implementations that |
3033 |
+# are not supported by the ebuild. |
3034 |
+# |
3035 |
+# Implementations in both variables are ordered using the pre-defined |
3036 |
+# eclass implementation ordering. |
3037 |
+# |
3038 |
+# This function must be called once in global scope by an eclass |
3039 |
+# utilizing PYTHON_COMPAT. |
3040 |
+_python_set_impls() { |
3041 |
+ local i |
3042 |
+ |
3043 |
+ if ! declare -p PYTHON_COMPAT &>/dev/null; then |
3044 |
+ die 'PYTHON_COMPAT not declared.' |
3045 |
+ fi |
3046 |
+ if [[ $(declare -p PYTHON_COMPAT) != "declare -a"* ]]; then |
3047 |
+ die 'PYTHON_COMPAT must be an array.' |
3048 |
+ fi |
3049 |
+ for i in "${PYTHON_COMPAT[@]}"; do |
3050 |
+ # trigger validity checks |
3051 |
+ _python_impl_supported "${i}" |
3052 |
+ done |
3053 |
+ |
3054 |
+ local supp=() unsupp=() |
3055 |
+ |
3056 |
+ for i in "${_PYTHON_ALL_IMPLS[@]}"; do |
3057 |
+ if has "${i}" "${PYTHON_COMPAT[@]}"; then |
3058 |
+ supp+=( "${i}" ) |
3059 |
+ else |
3060 |
+ unsupp+=( "${i}" ) |
3061 |
+ fi |
3062 |
+ done |
3063 |
+ |
3064 |
+ if [[ ! ${supp[@]} ]]; then |
3065 |
+ die "No supported implementation in PYTHON_COMPAT." |
3066 |
+ fi |
3067 |
+ |
3068 |
+ if [[ ${_PYTHON_SUPPORTED_IMPLS[@]} ]]; then |
3069 |
+ # set once already, verify integrity |
3070 |
+ if [[ ${_PYTHON_SUPPORTED_IMPLS[@]} != ${supp[@]} ]]; then |
3071 |
+ eerror "Supported impls (PYTHON_COMPAT) changed between inherits!" |
3072 |
+ eerror "Before: ${_PYTHON_SUPPORTED_IMPLS[*]}" |
3073 |
+ eerror "Now : ${supp[*]}" |
3074 |
+ die "_PYTHON_SUPPORTED_IMPLS integrity check failed" |
3075 |
+ fi |
3076 |
+ if [[ ${_PYTHON_UNSUPPORTED_IMPLS[@]} != ${unsupp[@]} ]]; then |
3077 |
+ eerror "Unsupported impls changed between inherits!" |
3078 |
+ eerror "Before: ${_PYTHON_UNSUPPORTED_IMPLS[*]}" |
3079 |
+ eerror "Now : ${unsupp[*]}" |
3080 |
+ die "_PYTHON_UNSUPPORTED_IMPLS integrity check failed" |
3081 |
+ fi |
3082 |
+ else |
3083 |
+ _PYTHON_SUPPORTED_IMPLS=( "${supp[@]}" ) |
3084 |
+ _PYTHON_UNSUPPORTED_IMPLS=( "${unsupp[@]}" ) |
3085 |
+ readonly _PYTHON_SUPPORTED_IMPLS _PYTHON_UNSUPPORTED_IMPLS |
3086 |
+ fi |
3087 |
+} |
3088 |
+ |
3089 |
+# @FUNCTION: _python_impl_matches |
3090 |
+# @USAGE: <impl> [<pattern>...] |
3091 |
+# @INTERNAL |
3092 |
+# @DESCRIPTION: |
3093 |
+# Check whether the specified <impl> matches at least one |
3094 |
+# of the patterns following it. Return 0 if it does, 1 otherwise. |
3095 |
+# Matches if no patterns are provided. |
3096 |
+# |
3097 |
+# <impl> can be in PYTHON_COMPAT or EPYTHON form. The patterns can be |
3098 |
+# either: |
3099 |
+# a) fnmatch-style patterns, e.g. 'python2*', 'pypy'... |
3100 |
+# b) '-2' to indicate all Python 2 variants (= !python_is_python3) |
3101 |
+# c) '-3' to indicate all Python 3 variants (= python_is_python3) |
3102 |
+_python_impl_matches() { |
3103 |
+ [[ ${#} -ge 1 ]] || die "${FUNCNAME}: takes at least 1 parameter" |
3104 |
+ [[ ${#} -eq 1 ]] && return 0 |
3105 |
+ |
3106 |
+ local impl=${1} pattern |
3107 |
+ shift |
3108 |
+ |
3109 |
+ for pattern; do |
3110 |
+ if [[ ${pattern} == -2 ]]; then |
3111 |
+ python_is_python3 "${impl}" || return 0 |
3112 |
+ elif [[ ${pattern} == -3 ]]; then |
3113 |
+ python_is_python3 "${impl}" && return 0 |
3114 |
+ return |
3115 |
+ # unify value style to allow lax matching |
3116 |
+ elif [[ ${impl/./_} == ${pattern/./_} ]]; then |
3117 |
+ return 0 |
3118 |
+ fi |
3119 |
+ done |
3120 |
+ |
3121 |
+ return 1 |
3122 |
+} |
3123 |
+ |
3124 |
+# @ECLASS-VARIABLE: PYTHON |
3125 |
+# @DEFAULT_UNSET |
3126 |
+# @DESCRIPTION: |
3127 |
+# The absolute path to the current Python interpreter. |
3128 |
+# |
3129 |
+# This variable is set automatically in the following contexts: |
3130 |
+# |
3131 |
+# python-r2: Set in functions called by python_foreach_impl() or after |
3132 |
+# calling python_export_best(). |
3133 |
+# |
3134 |
+# python-single-r2: Set after calling python-single-r2_pkg_setup(). |
3135 |
+# |
3136 |
+# distutils-r2: Set within any of the python sub-phase functions. |
3137 |
+# |
3138 |
+# Example value: |
3139 |
+# @CODE |
3140 |
+# /usr/bin/python2.7 |
3141 |
+# @CODE |
3142 |
+ |
3143 |
+# @ECLASS-VARIABLE: EPYTHON |
3144 |
+# @DEFAULT_UNSET |
3145 |
+# @DESCRIPTION: |
3146 |
+# The executable name of the current Python interpreter. |
3147 |
+# |
3148 |
+# This variable is set automatically in the following contexts: |
3149 |
+# |
3150 |
+# python-r2: Set in functions called by python_foreach_impl() or after |
3151 |
+# calling python_export_best(). |
3152 |
+# |
3153 |
+# python-single-r2: Set after calling python-single-r2_pkg_setup(). |
3154 |
+# |
3155 |
+# distutils-r2: Set within any of the python sub-phase functions. |
3156 |
+# |
3157 |
+# Example value: |
3158 |
+# @CODE |
3159 |
+# python2.7 |
3160 |
+# @CODE |
3161 |
+ |
3162 |
+# @ECLASS-VARIABLE: PYTHON_SITEDIR |
3163 |
+# @DEFAULT_UNSET |
3164 |
+# @DESCRIPTION: |
3165 |
+# The path to Python site-packages directory. |
3166 |
+# |
3167 |
+# Set and exported on request using python_export(). |
3168 |
+# Requires a proper build-time dependency on the Python implementation. |
3169 |
+# |
3170 |
+# Example value: |
3171 |
+# @CODE |
3172 |
+# /usr/lib64/python2.7/site-packages |
3173 |
+# @CODE |
3174 |
+ |
3175 |
+# @ECLASS-VARIABLE: PYTHON_INCLUDEDIR |
3176 |
+# @DEFAULT_UNSET |
3177 |
+# @DESCRIPTION: |
3178 |
+# The path to Python include directory. |
3179 |
+# |
3180 |
+# Set and exported on request using python_export(). |
3181 |
+# Requires a proper build-time dependency on the Python implementation. |
3182 |
+# |
3183 |
+# Example value: |
3184 |
+# @CODE |
3185 |
+# /usr/include/python2.7 |
3186 |
+# @CODE |
3187 |
+ |
3188 |
+# @ECLASS-VARIABLE: PYTHON_LIBPATH |
3189 |
+# @DEFAULT_UNSET |
3190 |
+# @DESCRIPTION: |
3191 |
+# The path to Python library. |
3192 |
+# |
3193 |
+# Set and exported on request using python_export(). |
3194 |
+# Valid only for CPython. Requires a proper build-time dependency |
3195 |
+# on the Python implementation. |
3196 |
+# |
3197 |
+# Example value: |
3198 |
+# @CODE |
3199 |
+# /usr/lib64/libpython2.7.so |
3200 |
+# @CODE |
3201 |
+ |
3202 |
+# @ECLASS-VARIABLE: PYTHON_CFLAGS |
3203 |
+# @DEFAULT_UNSET |
3204 |
+# @DESCRIPTION: |
3205 |
+# Proper C compiler flags for building against Python. Obtained from |
3206 |
+# pkg-config or python-config. |
3207 |
+# |
3208 |
+# Set and exported on request using python_export(). |
3209 |
+# Valid only for CPython. Requires a proper build-time dependency |
3210 |
+# on the Python implementation and on pkg-config. |
3211 |
+# |
3212 |
+# Example value: |
3213 |
+# @CODE |
3214 |
+# -I/usr/include/python2.7 |
3215 |
+# @CODE |
3216 |
+ |
3217 |
+# @ECLASS-VARIABLE: PYTHON_LIBS |
3218 |
+# @DEFAULT_UNSET |
3219 |
+# @DESCRIPTION: |
3220 |
+# Proper C compiler flags for linking against Python. Obtained from |
3221 |
+# pkg-config or python-config. |
3222 |
+# |
3223 |
+# Set and exported on request using python_export(). |
3224 |
+# Valid only for CPython. Requires a proper build-time dependency |
3225 |
+# on the Python implementation and on pkg-config. |
3226 |
+# |
3227 |
+# Example value: |
3228 |
+# @CODE |
3229 |
+# -lpython2.7 |
3230 |
+# @CODE |
3231 |
+ |
3232 |
+# @ECLASS-VARIABLE: PYTHON_CONFIG |
3233 |
+# @DEFAULT_UNSET |
3234 |
+# @DESCRIPTION: |
3235 |
+# Path to the python-config executable. |
3236 |
+# |
3237 |
+# Set and exported on request using python_export(). |
3238 |
+# Valid only for CPython. Requires a proper build-time dependency |
3239 |
+# on the Python implementation and on pkg-config. |
3240 |
+# |
3241 |
+# Example value: |
3242 |
+# @CODE |
3243 |
+# /usr/bin/python2.7-config |
3244 |
+# @CODE |
3245 |
+ |
3246 |
+# @ECLASS-VARIABLE: PYTHON_PKG_DEP |
3247 |
+# @DEFAULT_UNSET |
3248 |
+# @DESCRIPTION: |
3249 |
+# The complete dependency on a particular Python package as a string. |
3250 |
+# |
3251 |
+# Set and exported on request using python_export(). |
3252 |
+# |
3253 |
+# Example value: |
3254 |
+# @CODE |
3255 |
+# dev-lang/python:2.7[xml] |
3256 |
+# @CODE |
3257 |
+ |
3258 |
+# @ECLASS-VARIABLE: PYTHON_SCRIPTDIR |
3259 |
+# @DEFAULT_UNSET |
3260 |
+# @DESCRIPTION: |
3261 |
+# The location where Python scripts must be installed for current impl. |
3262 |
+# |
3263 |
+# Set and exported on request using python_export(). |
3264 |
+# |
3265 |
+# Example value: |
3266 |
+# @CODE |
3267 |
+# /usr/lib/python-exec/python2.7 |
3268 |
+# @CODE |
3269 |
+ |
3270 |
+# @FUNCTION: python_export |
3271 |
+# @USAGE: [<impl>] <variables>... |
3272 |
+# @DESCRIPTION: |
3273 |
+# Set and export the Python implementation-relevant variables passed |
3274 |
+# as parameters. |
3275 |
+# |
3276 |
+# The optional first parameter may specify the requested Python |
3277 |
+# implementation (either as PYTHON_TARGETS value, e.g. python2_7, |
3278 |
+# or an EPYTHON one, e.g. python2.7). If no implementation passed, |
3279 |
+# the current one will be obtained from ${EPYTHON}. |
3280 |
+# |
3281 |
+# The variables which can be exported are: PYTHON, EPYTHON, |
3282 |
+# PYTHON_SITEDIR. They are described more completely in the eclass |
3283 |
+# variable documentation. |
3284 |
+python_export() { |
3285 |
+ debug-print-function ${FUNCNAME} "${@}" |
3286 |
+ |
3287 |
+ local impl var |
3288 |
+ |
3289 |
+ case "${1}" in |
3290 |
+ python*|jython*) |
3291 |
+ impl=${1/_/.} |
3292 |
+ shift |
3293 |
+ ;; |
3294 |
+ pypy|pypy3) |
3295 |
+ impl=${1} |
3296 |
+ shift |
3297 |
+ ;; |
3298 |
+ *) |
3299 |
+ impl=${EPYTHON} |
3300 |
+ if [[ -z ${impl} ]]; then |
3301 |
+ die "python_export called without a python implementation and EPYTHON is unset" |
3302 |
+ fi |
3303 |
+ ;; |
3304 |
+ esac |
3305 |
+ debug-print "${FUNCNAME}: implementation: ${impl}" |
3306 |
+ |
3307 |
+ for var; do |
3308 |
+ case "${var}" in |
3309 |
+ EPYTHON) |
3310 |
+ export EPYTHON=${impl} |
3311 |
+ debug-print "${FUNCNAME}: EPYTHON = ${EPYTHON}" |
3312 |
+ ;; |
3313 |
+ PYTHON) |
3314 |
+ export PYTHON=${EPREFIX}/usr/bin/${impl} |
3315 |
+ debug-print "${FUNCNAME}: PYTHON = ${PYTHON}" |
3316 |
+ ;; |
3317 |
+ PYTHON_SITEDIR) |
3318 |
+ [[ -n ${PYTHON} ]] || die "PYTHON needs to be set for ${var} to be exported, or requested before it" |
3319 |
+ # sysconfig can't be used because: |
3320 |
+ # 1) pypy doesn't give site-packages but stdlib |
3321 |
+ # 2) jython gives paths with wrong case |
3322 |
+ PYTHON_SITEDIR=$("${PYTHON}" -c 'import distutils.sysconfig; print(distutils.sysconfig.get_python_lib())') || die |
3323 |
+ export PYTHON_SITEDIR |
3324 |
+ debug-print "${FUNCNAME}: PYTHON_SITEDIR = ${PYTHON_SITEDIR}" |
3325 |
+ ;; |
3326 |
+ PYTHON_INCLUDEDIR) |
3327 |
+ [[ -n ${PYTHON} ]] || die "PYTHON needs to be set for ${var} to be exported, or requested before it" |
3328 |
+ PYTHON_INCLUDEDIR=$("${PYTHON}" -c 'import distutils.sysconfig; print(distutils.sysconfig.get_python_inc())') || die |
3329 |
+ export PYTHON_INCLUDEDIR |
3330 |
+ debug-print "${FUNCNAME}: PYTHON_INCLUDEDIR = ${PYTHON_INCLUDEDIR}" |
3331 |
+ |
3332 |
+ # Jython gives a non-existing directory |
3333 |
+ if [[ ! -d ${PYTHON_INCLUDEDIR} ]]; then |
3334 |
+ die "${impl} does not install any header files!" |
3335 |
+ fi |
3336 |
+ ;; |
3337 |
+ PYTHON_LIBPATH) |
3338 |
+ [[ -n ${PYTHON} ]] || die "PYTHON needs to be set for ${var} to be exported, or requested before it" |
3339 |
+ PYTHON_LIBPATH=$("${PYTHON}" -c 'import os.path, sysconfig; print(os.path.join(sysconfig.get_config_var("LIBDIR"), sysconfig.get_config_var("LDLIBRARY")) if sysconfig.get_config_var("LDLIBRARY") else "")') || die |
3340 |
+ export PYTHON_LIBPATH |
3341 |
+ debug-print "${FUNCNAME}: PYTHON_LIBPATH = ${PYTHON_LIBPATH}" |
3342 |
+ |
3343 |
+ if [[ ! ${PYTHON_LIBPATH} ]]; then |
3344 |
+ die "${impl} lacks a (usable) dynamic library" |
3345 |
+ fi |
3346 |
+ ;; |
3347 |
+ PYTHON_CFLAGS) |
3348 |
+ local val |
3349 |
+ |
3350 |
+ case "${impl}" in |
3351 |
+ python*) |
3352 |
+ # python-2.7, python-3.2, etc. |
3353 |
+ val=$($(tc-getPKG_CONFIG) --cflags ${impl/n/n-}) || die |
3354 |
+ ;; |
3355 |
+ *) |
3356 |
+ die "${impl}: obtaining ${var} not supported" |
3357 |
+ ;; |
3358 |
+ esac |
3359 |
+ |
3360 |
+ export PYTHON_CFLAGS=${val} |
3361 |
+ debug-print "${FUNCNAME}: PYTHON_CFLAGS = ${PYTHON_CFLAGS}" |
3362 |
+ ;; |
3363 |
+ PYTHON_LIBS) |
3364 |
+ local val |
3365 |
+ |
3366 |
+ case "${impl}" in |
3367 |
+ python*) |
3368 |
+ # python-2.7, python-3.2, etc. |
3369 |
+ val=$($(tc-getPKG_CONFIG) --libs ${impl/n/n-}) || die |
3370 |
+ ;; |
3371 |
+ *) |
3372 |
+ die "${impl}: obtaining ${var} not supported" |
3373 |
+ ;; |
3374 |
+ esac |
3375 |
+ |
3376 |
+ export PYTHON_LIBS=${val} |
3377 |
+ debug-print "${FUNCNAME}: PYTHON_LIBS = ${PYTHON_LIBS}" |
3378 |
+ ;; |
3379 |
+ PYTHON_CONFIG) |
3380 |
+ local flags val |
3381 |
+ |
3382 |
+ case "${impl}" in |
3383 |
+ python*) |
3384 |
+ [[ -n ${PYTHON} ]] || die "PYTHON needs to be set for ${var} to be exported, or requested before it" |
3385 |
+ flags=$("${PYTHON}" -c 'import sysconfig; print(sysconfig.get_config_var("ABIFLAGS") or "")') || die |
3386 |
+ val=${PYTHON}${flags}-config |
3387 |
+ ;; |
3388 |
+ *) |
3389 |
+ die "${impl}: obtaining ${var} not supported" |
3390 |
+ ;; |
3391 |
+ esac |
3392 |
+ |
3393 |
+ export PYTHON_CONFIG=${val} |
3394 |
+ debug-print "${FUNCNAME}: PYTHON_CONFIG = ${PYTHON_CONFIG}" |
3395 |
+ ;; |
3396 |
+ PYTHON_PKG_DEP) |
3397 |
+ local d |
3398 |
+ case ${impl} in |
3399 |
+ python2.7) |
3400 |
+ PYTHON_PKG_DEP='>=dev-lang/python-2.7.5-r2:2.7';; |
3401 |
+ python3.3) |
3402 |
+ PYTHON_PKG_DEP='>=dev-lang/python-3.3.2-r2:3.3';; |
3403 |
+ python*) |
3404 |
+ PYTHON_PKG_DEP="dev-lang/python:${impl#python}";; |
3405 |
+ pypy) |
3406 |
+ PYTHON_PKG_DEP='>=dev-python/pypy-5:0=';; |
3407 |
+ pypy3) |
3408 |
+ PYTHON_PKG_DEP='>=dev-python/pypy3-5:0=';; |
3409 |
+ jython2.7) |
3410 |
+ PYTHON_PKG_DEP='dev-java/jython:2.7';; |
3411 |
+ *) |
3412 |
+ die "Invalid implementation: ${impl}" |
3413 |
+ esac |
3414 |
+ |
3415 |
+ # use-dep |
3416 |
+ if [[ ${PYTHON_REQ_USE} ]]; then |
3417 |
+ PYTHON_PKG_DEP+=[${PYTHON_REQ_USE}] |
3418 |
+ fi |
3419 |
+ |
3420 |
+ export PYTHON_PKG_DEP |
3421 |
+ debug-print "${FUNCNAME}: PYTHON_PKG_DEP = ${PYTHON_PKG_DEP}" |
3422 |
+ ;; |
3423 |
+ PYTHON_SCRIPTDIR) |
3424 |
+ local dir |
3425 |
+ export PYTHON_SCRIPTDIR=${EPREFIX}/usr/lib/python-exec/${impl} |
3426 |
+ debug-print "${FUNCNAME}: PYTHON_SCRIPTDIR = ${PYTHON_SCRIPTDIR}" |
3427 |
+ ;; |
3428 |
+ *) |
3429 |
+ die "python_export: unknown variable ${var}" |
3430 |
+ esac |
3431 |
+ done |
3432 |
+} |
3433 |
+ |
3434 |
+# @FUNCTION: python_get_sitedir |
3435 |
+# @USAGE: [<impl>] |
3436 |
+# @DESCRIPTION: |
3437 |
+# Obtain and print the 'site-packages' path for the given |
3438 |
+# implementation. If no implementation is provided, ${EPYTHON} will |
3439 |
+# be used. |
3440 |
+# |
3441 |
+# If you just need to have PYTHON_SITEDIR set (and exported), then it is |
3442 |
+# better to use python_export() directly instead. |
3443 |
+python_get_sitedir() { |
3444 |
+ debug-print-function ${FUNCNAME} "${@}" |
3445 |
+ |
3446 |
+ python_export "${@}" PYTHON_SITEDIR |
3447 |
+ echo "${PYTHON_SITEDIR}" |
3448 |
+} |
3449 |
+ |
3450 |
+# @FUNCTION: python_get_includedir |
3451 |
+# @USAGE: [<impl>] |
3452 |
+# @DESCRIPTION: |
3453 |
+# Obtain and print the include path for the given implementation. If no |
3454 |
+# implementation is provided, ${EPYTHON} will be used. |
3455 |
+# |
3456 |
+# If you just need to have PYTHON_INCLUDEDIR set (and exported), then it |
3457 |
+# is better to use python_export() directly instead. |
3458 |
+python_get_includedir() { |
3459 |
+ debug-print-function ${FUNCNAME} "${@}" |
3460 |
+ |
3461 |
+ python_export "${@}" PYTHON_INCLUDEDIR |
3462 |
+ echo "${PYTHON_INCLUDEDIR}" |
3463 |
+} |
3464 |
+ |
3465 |
+# @FUNCTION: python_get_library_path |
3466 |
+# @USAGE: [<impl>] |
3467 |
+# @DESCRIPTION: |
3468 |
+# Obtain and print the Python library path for the given implementation. |
3469 |
+# If no implementation is provided, ${EPYTHON} will be used. |
3470 |
+# |
3471 |
+# Please note that this function can be used with CPython only. Use |
3472 |
+# in another implementation will result in a fatal failure. |
3473 |
+python_get_library_path() { |
3474 |
+ debug-print-function ${FUNCNAME} "${@}" |
3475 |
+ |
3476 |
+ python_export "${@}" PYTHON_LIBPATH |
3477 |
+ echo "${PYTHON_LIBPATH}" |
3478 |
+} |
3479 |
+ |
3480 |
+# @FUNCTION: python_get_CFLAGS |
3481 |
+# @USAGE: [<impl>] |
3482 |
+# @DESCRIPTION: |
3483 |
+# Obtain and print the compiler flags for building against Python, |
3484 |
+# for the given implementation. If no implementation is provided, |
3485 |
+# ${EPYTHON} will be used. |
3486 |
+# |
3487 |
+# Please note that this function can be used with CPython only. |
3488 |
+# It requires Python and pkg-config installed, and therefore proper |
3489 |
+# build-time dependencies need be added to the ebuild. |
3490 |
+python_get_CFLAGS() { |
3491 |
+ debug-print-function ${FUNCNAME} "${@}" |
3492 |
+ |
3493 |
+ python_export "${@}" PYTHON_CFLAGS |
3494 |
+ echo "${PYTHON_CFLAGS}" |
3495 |
+} |
3496 |
+ |
3497 |
+# @FUNCTION: python_get_LIBS |
3498 |
+# @USAGE: [<impl>] |
3499 |
+# @DESCRIPTION: |
3500 |
+# Obtain and print the compiler flags for linking against Python, |
3501 |
+# for the given implementation. If no implementation is provided, |
3502 |
+# ${EPYTHON} will be used. |
3503 |
+# |
3504 |
+# Please note that this function can be used with CPython only. |
3505 |
+# It requires Python and pkg-config installed, and therefore proper |
3506 |
+# build-time dependencies need be added to the ebuild. |
3507 |
+python_get_LIBS() { |
3508 |
+ debug-print-function ${FUNCNAME} "${@}" |
3509 |
+ |
3510 |
+ python_export "${@}" PYTHON_LIBS |
3511 |
+ echo "${PYTHON_LIBS}" |
3512 |
+} |
3513 |
+ |
3514 |
+# @FUNCTION: python_get_PYTHON_CONFIG |
3515 |
+# @USAGE: [<impl>] |
3516 |
+# @DESCRIPTION: |
3517 |
+# Obtain and print the PYTHON_CONFIG location for the given |
3518 |
+# implementation. If no implementation is provided, ${EPYTHON} will be |
3519 |
+# used. |
3520 |
+# |
3521 |
+# Please note that this function can be used with CPython only. |
3522 |
+# It requires Python installed, and therefore proper build-time |
3523 |
+# dependencies need be added to the ebuild. |
3524 |
+python_get_PYTHON_CONFIG() { |
3525 |
+ debug-print-function ${FUNCNAME} "${@}" |
3526 |
+ |
3527 |
+ python_export "${@}" PYTHON_CONFIG |
3528 |
+ echo "${PYTHON_CONFIG}" |
3529 |
+} |
3530 |
+ |
3531 |
+# @FUNCTION: python_get_scriptdir |
3532 |
+# @USAGE: [<impl>] |
3533 |
+# @DESCRIPTION: |
3534 |
+# Obtain and print the script install path for the given |
3535 |
+# implementation. If no implementation is provided, ${EPYTHON} will |
3536 |
+# be used. |
3537 |
+python_get_scriptdir() { |
3538 |
+ debug-print-function ${FUNCNAME} "${@}" |
3539 |
+ |
3540 |
+ python_export "${@}" PYTHON_SCRIPTDIR |
3541 |
+ echo "${PYTHON_SCRIPTDIR}" |
3542 |
+} |
3543 |
+ |
3544 |
+# @FUNCTION: _python_ln_rel |
3545 |
+# @USAGE: <from> <to> |
3546 |
+# @INTERNAL |
3547 |
+# @DESCRIPTION: |
3548 |
+# Create a relative symlink. |
3549 |
+_python_ln_rel() { |
3550 |
+ debug-print-function ${FUNCNAME} "${@}" |
3551 |
+ |
3552 |
+ local target=${1} |
3553 |
+ local symname=${2} |
3554 |
+ |
3555 |
+ local tgpath=${target%/*}/ |
3556 |
+ local sympath=${symname%/*}/ |
3557 |
+ local rel_target= |
3558 |
+ |
3559 |
+ while [[ ${sympath} ]]; do |
3560 |
+ local tgseg= symseg= |
3561 |
+ |
3562 |
+ while [[ ! ${tgseg} && ${tgpath} ]]; do |
3563 |
+ tgseg=${tgpath%%/*} |
3564 |
+ tgpath=${tgpath#${tgseg}/} |
3565 |
+ done |
3566 |
+ |
3567 |
+ while [[ ! ${symseg} && ${sympath} ]]; do |
3568 |
+ symseg=${sympath%%/*} |
3569 |
+ sympath=${sympath#${symseg}/} |
3570 |
+ done |
3571 |
+ |
3572 |
+ if [[ ${tgseg} != ${symseg} ]]; then |
3573 |
+ rel_target=../${rel_target}${tgseg:+${tgseg}/} |
3574 |
+ fi |
3575 |
+ done |
3576 |
+ rel_target+=${tgpath}${target##*/} |
3577 |
+ |
3578 |
+ debug-print "${FUNCNAME}: ${symname} -> ${target}" |
3579 |
+ debug-print "${FUNCNAME}: rel_target = ${rel_target}" |
3580 |
+ |
3581 |
+ ln -fs "${rel_target}" "${symname}" |
3582 |
+} |
3583 |
+ |
3584 |
+# @FUNCTION: python_optimize |
3585 |
+# @USAGE: [<directory>...] |
3586 |
+# @DESCRIPTION: |
3587 |
+# Compile and optimize Python modules in specified directories (absolute |
3588 |
+# paths). If no directories are provided, the default system paths |
3589 |
+# are used (prepended with ${D}). |
3590 |
+python_optimize() { |
3591 |
+ debug-print-function ${FUNCNAME} "${@}" |
3592 |
+ |
3593 |
+ if [[ ${EBUILD_PHASE} == pre* || ${EBUILD_PHASE} == post* ]]; then |
3594 |
+ eerror "The new Python eclasses expect the compiled Python files to" |
3595 |
+ eerror "be controlled by the Package Manager. For this reason," |
3596 |
+ eerror "the python_optimize function can be used only during src_* phases" |
3597 |
+ eerror "(src_install most commonly) and not during pkg_* phases." |
3598 |
+ echo |
3599 |
+ die "python_optimize is not to be used in pre/post* phases" |
3600 |
+ fi |
3601 |
+ |
3602 |
+ [[ ${EPYTHON} ]] || die 'No Python implementation set (EPYTHON is null).' |
3603 |
+ |
3604 |
+ local PYTHON=${PYTHON} |
3605 |
+ [[ ${PYTHON} ]] || python_export PYTHON |
3606 |
+ |
3607 |
+ # default to sys.path |
3608 |
+ if [[ ${#} -eq 0 ]]; then |
3609 |
+ local f |
3610 |
+ while IFS= read -r -d '' f; do |
3611 |
+ # 1) accept only absolute paths |
3612 |
+ # (i.e. skip '', '.' or anything like that) |
3613 |
+ # 2) skip paths which do not exist |
3614 |
+ # (python2.6 complains about them verbosely) |
3615 |
+ |
3616 |
+ if [[ ${f} == /* && -d ${D%/}${f} ]]; then |
3617 |
+ set -- "${D%/}${f}" "${@}" |
3618 |
+ fi |
3619 |
+ done < <("${PYTHON}" -c 'import sys; print("".join(x + "\0" for x in sys.path))' || die) |
3620 |
+ |
3621 |
+ debug-print "${FUNCNAME}: using sys.path: ${*/%/;}" |
3622 |
+ fi |
3623 |
+ |
3624 |
+ local d |
3625 |
+ for d; do |
3626 |
+ # make sure to get a nice path without // |
3627 |
+ local instpath=${d#${D%/}} |
3628 |
+ instpath=/${instpath##/} |
3629 |
+ |
3630 |
+ case "${EPYTHON}" in |
3631 |
+ python2.7|python3.[34]) |
3632 |
+ "${PYTHON}" -m compileall -q -f -d "${instpath}" "${d}" |
3633 |
+ "${PYTHON}" -OO -m compileall -q -f -d "${instpath}" "${d}" |
3634 |
+ ;; |
3635 |
+ python*|pypy3) |
3636 |
+ # both levels of optimization are separate since 3.5 |
3637 |
+ "${PYTHON}" -m compileall -q -f -d "${instpath}" "${d}" |
3638 |
+ "${PYTHON}" -O -m compileall -q -f -d "${instpath}" "${d}" |
3639 |
+ "${PYTHON}" -OO -m compileall -q -f -d "${instpath}" "${d}" |
3640 |
+ ;; |
3641 |
+ *) |
3642 |
+ "${PYTHON}" -m compileall -q -f -d "${instpath}" "${d}" |
3643 |
+ ;; |
3644 |
+ esac |
3645 |
+ done |
3646 |
+} |
3647 |
+ |
3648 |
+# @FUNCTION: python_scriptinto |
3649 |
+# @USAGE: <new-path> |
3650 |
+# @DESCRIPTION: |
3651 |
+# Set the directory to which files passed to python_doexe(), |
3652 |
+# python_doscript(), python_newexe() and python_newscript() |
3653 |
+# are going to be installed. The new value needs to be relative |
3654 |
+# to the installation root (${ED}). |
3655 |
+# |
3656 |
+# If not set explicitly, the directory defaults to /usr/bin. |
3657 |
+# |
3658 |
+# Example: |
3659 |
+# @CODE |
3660 |
+# src_install() { |
3661 |
+# python_scriptinto /usr/sbin |
3662 |
+# python_foreach_impl python_doscript foo |
3663 |
+# } |
3664 |
+# @CODE |
3665 |
+python_scriptinto() { |
3666 |
+ debug-print-function ${FUNCNAME} "${@}" |
3667 |
+ |
3668 |
+ python_scriptroot=${1} |
3669 |
+} |
3670 |
+ |
3671 |
+# @FUNCTION: python_doexe |
3672 |
+# @USAGE: <files>... |
3673 |
+# @DESCRIPTION: |
3674 |
+# Install the given executables into the executable install directory, |
3675 |
+# for the current Python implementation (${EPYTHON}). |
3676 |
+# |
3677 |
+# The executable will be wrapped properly for the Python implementation, |
3678 |
+# though no shebang mangling will be performed. |
3679 |
+python_doexe() { |
3680 |
+ debug-print-function ${FUNCNAME} "${@}" |
3681 |
+ |
3682 |
+ local f |
3683 |
+ for f; do |
3684 |
+ python_newexe "${f}" "${f##*/}" |
3685 |
+ done |
3686 |
+} |
3687 |
+ |
3688 |
+# @FUNCTION: python_newexe |
3689 |
+# @USAGE: <path> <new-name> |
3690 |
+# @DESCRIPTION: |
3691 |
+# Install the given executable into the executable install directory, |
3692 |
+# for the current Python implementation (${EPYTHON}). |
3693 |
+# |
3694 |
+# The executable will be wrapped properly for the Python implementation, |
3695 |
+# though no shebang mangling will be performed. It will be renamed |
3696 |
+# to <new-name>. |
3697 |
+python_newexe() { |
3698 |
+ debug-print-function ${FUNCNAME} "${@}" |
3699 |
+ |
3700 |
+ [[ ${EPYTHON} ]] || die 'No Python implementation set (EPYTHON is null).' |
3701 |
+ [[ ${#} -eq 2 ]] || die "Usage: ${FUNCNAME} <path> <new-name>" |
3702 |
+ |
3703 |
+ local wrapd=${python_scriptroot:-/usr/bin} |
3704 |
+ |
3705 |
+ local f=${1} |
3706 |
+ local newfn=${2} |
3707 |
+ |
3708 |
+ local PYTHON_SCRIPTDIR d |
3709 |
+ python_export PYTHON_SCRIPTDIR |
3710 |
+ d=${PYTHON_SCRIPTDIR#${EPREFIX}} |
3711 |
+ |
3712 |
+ ( |
3713 |
+ dodir "${wrapd}" |
3714 |
+ exeopts -m 0755 |
3715 |
+ exeinto "${d}" |
3716 |
+ newexe "${f}" "${newfn}" || return ${?} |
3717 |
+ ) |
3718 |
+ |
3719 |
+ # install the wrapper |
3720 |
+ _python_ln_rel "${ED%/}"/usr/lib/python-exec/python-exec2 \ |
3721 |
+ "${ED%/}/${wrapd}/${newfn}" || die |
3722 |
+ |
3723 |
+ # don't use this at home, just call python_doscript() instead |
3724 |
+ if [[ ${_PYTHON_REWRITE_SHEBANG} ]]; then |
3725 |
+ python_fix_shebang -q "${ED%/}/${d}/${newfn}" |
3726 |
+ fi |
3727 |
+} |
3728 |
+ |
3729 |
+# @FUNCTION: python_doscript |
3730 |
+# @USAGE: <files>... |
3731 |
+# @DESCRIPTION: |
3732 |
+# Install the given scripts into the executable install directory, |
3733 |
+# for the current Python implementation (${EPYTHON}). |
3734 |
+# |
3735 |
+# All specified files must start with a 'python' shebang. The shebang |
3736 |
+# will be converted, and the files will be wrapped properly |
3737 |
+# for the Python implementation. |
3738 |
+# |
3739 |
+# Example: |
3740 |
+# @CODE |
3741 |
+# src_install() { |
3742 |
+# python_foreach_impl python_doscript ${PN} |
3743 |
+# } |
3744 |
+# @CODE |
3745 |
+python_doscript() { |
3746 |
+ debug-print-function ${FUNCNAME} "${@}" |
3747 |
+ |
3748 |
+ local _PYTHON_REWRITE_SHEBANG=1 |
3749 |
+ python_doexe "${@}" |
3750 |
+} |
3751 |
+ |
3752 |
+# @FUNCTION: python_newscript |
3753 |
+# @USAGE: <path> <new-name> |
3754 |
+# @DESCRIPTION: |
3755 |
+# Install the given script into the executable install directory |
3756 |
+# for the current Python implementation (${EPYTHON}), and name it |
3757 |
+# <new-name>. |
3758 |
+# |
3759 |
+# The file must start with a 'python' shebang. The shebang will be |
3760 |
+# converted, and the file will be wrapped properly for the Python |
3761 |
+# implementation. It will be renamed to <new-name>. |
3762 |
+# |
3763 |
+# Example: |
3764 |
+# @CODE |
3765 |
+# src_install() { |
3766 |
+# python_foreach_impl python_newscript foo.py foo |
3767 |
+# } |
3768 |
+# @CODE |
3769 |
+python_newscript() { |
3770 |
+ debug-print-function ${FUNCNAME} "${@}" |
3771 |
+ |
3772 |
+ local _PYTHON_REWRITE_SHEBANG=1 |
3773 |
+ python_newexe "${@}" |
3774 |
+} |
3775 |
+ |
3776 |
+# @FUNCTION: python_moduleinto |
3777 |
+# @USAGE: <new-path> |
3778 |
+# @DESCRIPTION: |
3779 |
+# Set the Python module install directory for python_domodule(). |
3780 |
+# The <new-path> can either be an absolute target system path (in which |
3781 |
+# case it needs to start with a slash, and ${ED} will be prepended to |
3782 |
+# it) or relative to the implementation's site-packages directory |
3783 |
+# (then it must not start with a slash). The relative path can be |
3784 |
+# specified either using the Python package notation (separated by dots) |
3785 |
+# or the directory notation (using slashes). |
3786 |
+# |
3787 |
+# When not set explicitly, the modules are installed to the top |
3788 |
+# site-packages directory. |
3789 |
+# |
3790 |
+# In the relative case, the exact path is determined directly |
3791 |
+# by each python_doscript/python_newscript function. Therefore, |
3792 |
+# python_moduleinto can be safely called before establishing the Python |
3793 |
+# interpreter and/or a single call can be used to set the path correctly |
3794 |
+# for multiple implementations, as can be seen in the following example. |
3795 |
+# |
3796 |
+# Example: |
3797 |
+# @CODE |
3798 |
+# src_install() { |
3799 |
+# python_moduleinto bar |
3800 |
+# # installs ${PYTHON_SITEDIR}/bar/baz.py |
3801 |
+# python_foreach_impl python_domodule baz.py |
3802 |
+# } |
3803 |
+# @CODE |
3804 |
+python_moduleinto() { |
3805 |
+ debug-print-function ${FUNCNAME} "${@}" |
3806 |
+ |
3807 |
+ python_moduleroot=${1} |
3808 |
+} |
3809 |
+ |
3810 |
+# @FUNCTION: python_domodule |
3811 |
+# @USAGE: <files>... |
3812 |
+# @DESCRIPTION: |
3813 |
+# Install the given modules (or packages) into the current Python module |
3814 |
+# installation directory. The list can mention both modules (files) |
3815 |
+# and packages (directories). All listed files will be installed |
3816 |
+# for all enabled implementations, and compiled afterwards. |
3817 |
+# |
3818 |
+# Example: |
3819 |
+# @CODE |
3820 |
+# src_install() { |
3821 |
+# # (${PN} being a directory) |
3822 |
+# python_foreach_impl python_domodule ${PN} |
3823 |
+# } |
3824 |
+# @CODE |
3825 |
+python_domodule() { |
3826 |
+ debug-print-function ${FUNCNAME} "${@}" |
3827 |
+ |
3828 |
+ [[ ${EPYTHON} ]] || die 'No Python implementation set (EPYTHON is null).' |
3829 |
+ |
3830 |
+ local d |
3831 |
+ if [[ ${python_moduleroot} == /* ]]; then |
3832 |
+ # absolute path |
3833 |
+ d=${python_moduleroot} |
3834 |
+ else |
3835 |
+ # relative to site-packages |
3836 |
+ local PYTHON_SITEDIR=${PYTHON_SITEDIR} |
3837 |
+ [[ ${PYTHON_SITEDIR} ]] || python_export PYTHON_SITEDIR |
3838 |
+ |
3839 |
+ d=${PYTHON_SITEDIR#${EPREFIX}}/${python_moduleroot//.//} |
3840 |
+ fi |
3841 |
+ |
3842 |
+ ( |
3843 |
+ insopts -m 0644 |
3844 |
+ insinto "${d}" |
3845 |
+ doins -r "${@}" || return ${?} |
3846 |
+ ) |
3847 |
+ |
3848 |
+ python_optimize "${ED%/}/${d}" |
3849 |
+} |
3850 |
+ |
3851 |
+# @FUNCTION: python_doheader |
3852 |
+# @USAGE: <files>... |
3853 |
+# @DESCRIPTION: |
3854 |
+# Install the given headers into the implementation-specific include |
3855 |
+# directory. This function is unconditionally recursive, i.e. you can |
3856 |
+# pass directories instead of files. |
3857 |
+# |
3858 |
+# Example: |
3859 |
+# @CODE |
3860 |
+# src_install() { |
3861 |
+# python_foreach_impl python_doheader foo.h bar.h |
3862 |
+# } |
3863 |
+# @CODE |
3864 |
+python_doheader() { |
3865 |
+ debug-print-function ${FUNCNAME} "${@}" |
3866 |
+ |
3867 |
+ [[ ${EPYTHON} ]] || die 'No Python implementation set (EPYTHON is null).' |
3868 |
+ |
3869 |
+ local d PYTHON_INCLUDEDIR=${PYTHON_INCLUDEDIR} |
3870 |
+ [[ ${PYTHON_INCLUDEDIR} ]] || python_export PYTHON_INCLUDEDIR |
3871 |
+ |
3872 |
+ d=${PYTHON_INCLUDEDIR#${EPREFIX}} |
3873 |
+ |
3874 |
+ ( |
3875 |
+ insopts -m 0644 |
3876 |
+ insinto "${d}" |
3877 |
+ doins -r "${@}" || return ${?} |
3878 |
+ ) |
3879 |
+} |
3880 |
+ |
3881 |
+# @FUNCTION: python_wrapper_setup |
3882 |
+# @USAGE: [<path> [<impl>]] |
3883 |
+# @DESCRIPTION: |
3884 |
+# Create proper 'python' executable and pkg-config wrappers |
3885 |
+# (if available) in the directory named by <path>. Set up PATH |
3886 |
+# and PKG_CONFIG_PATH appropriately. <path> defaults to ${T}/${EPYTHON}. |
3887 |
+# |
3888 |
+# The wrappers will be created for implementation named by <impl>, |
3889 |
+# or for one named by ${EPYTHON} if no <impl> passed. |
3890 |
+# |
3891 |
+# If the named directory contains a python symlink already, it will |
3892 |
+# be assumed to contain proper wrappers already and only environment |
3893 |
+# setup will be done. If wrapper update is requested, the directory |
3894 |
+# shall be removed first. |
3895 |
+python_wrapper_setup() { |
3896 |
+ debug-print-function ${FUNCNAME} "${@}" |
3897 |
+ |
3898 |
+ local workdir=${1:-${T}/${EPYTHON}} |
3899 |
+ local impl=${2:-${EPYTHON}} |
3900 |
+ |
3901 |
+ [[ ${workdir} ]] || die "${FUNCNAME}: no workdir specified." |
3902 |
+ [[ ${impl} ]] || die "${FUNCNAME}: no impl nor EPYTHON specified." |
3903 |
+ |
3904 |
+ if [[ ! -x ${workdir}/bin/python ]]; then |
3905 |
+ _python_check_dead_variables |
3906 |
+ |
3907 |
+ mkdir -p "${workdir}"/{bin,pkgconfig} || die |
3908 |
+ |
3909 |
+ # Clean up, in case we were supposed to do a cheap update. |
3910 |
+ rm -f "${workdir}"/bin/python{,2,3}{,-config} || die |
3911 |
+ rm -f "${workdir}"/bin/2to3 || die |
3912 |
+ rm -f "${workdir}"/pkgconfig/python{,2,3}.pc || die |
3913 |
+ |
3914 |
+ local EPYTHON PYTHON |
3915 |
+ python_export "${impl}" EPYTHON PYTHON |
3916 |
+ |
3917 |
+ local pyver pyother |
3918 |
+ if python_is_python3; then |
3919 |
+ pyver=3 |
3920 |
+ pyother=2 |
3921 |
+ else |
3922 |
+ pyver=2 |
3923 |
+ pyother=3 |
3924 |
+ fi |
3925 |
+ |
3926 |
+ # Python interpreter |
3927 |
+ # note: we don't use symlinks because python likes to do some |
3928 |
+ # symlink reading magic that breaks stuff |
3929 |
+ # https://bugs.gentoo.org/show_bug.cgi?id=555752 |
3930 |
+ cat > "${workdir}/bin/python" <<-_EOF_ || die |
3931 |
+ #!/bin/sh |
3932 |
+ exec "${PYTHON}" "\${@}" |
3933 |
+ _EOF_ |
3934 |
+ cp "${workdir}/bin/python" "${workdir}/bin/python${pyver}" || die |
3935 |
+ chmod +x "${workdir}/bin/python" "${workdir}/bin/python${pyver}" || die |
3936 |
+ |
3937 |
+ local nonsupp=( "python${pyother}" "python${pyother}-config" ) |
3938 |
+ |
3939 |
+ # CPython-specific |
3940 |
+ if [[ ${EPYTHON} == python* ]]; then |
3941 |
+ cat > "${workdir}/bin/python-config" <<-_EOF_ || die |
3942 |
+ #!/bin/sh |
3943 |
+ exec "${PYTHON}-config" "\${@}" |
3944 |
+ _EOF_ |
3945 |
+ cp "${workdir}/bin/python-config" \ |
3946 |
+ "${workdir}/bin/python${pyver}-config" || die |
3947 |
+ chmod +x "${workdir}/bin/python-config" \ |
3948 |
+ "${workdir}/bin/python${pyver}-config" || die |
3949 |
+ |
3950 |
+ # Python 2.6+. |
3951 |
+ ln -s "${PYTHON/python/2to3-}" "${workdir}"/bin/2to3 || die |
3952 |
+ |
3953 |
+ # Python 2.7+. |
3954 |
+ ln -s "${EPREFIX}"/usr/$(get_libdir)/pkgconfig/${EPYTHON/n/n-}.pc \ |
3955 |
+ "${workdir}"/pkgconfig/python.pc || die |
3956 |
+ ln -s python.pc "${workdir}"/pkgconfig/python${pyver}.pc || die |
3957 |
+ else |
3958 |
+ nonsupp+=( 2to3 python-config "python${pyver}-config" ) |
3959 |
+ fi |
3960 |
+ |
3961 |
+ local x |
3962 |
+ for x in "${nonsupp[@]}"; do |
3963 |
+ cat >"${workdir}"/bin/${x} <<-_EOF_ || die |
3964 |
+ #!/bin/sh |
3965 |
+ echo "${ECLASS}: ${FUNCNAME}: ${x} is not supported by ${EPYTHON} (PYTHON_COMPAT)" >&2 |
3966 |
+ exit 127 |
3967 |
+ _EOF_ |
3968 |
+ chmod +x "${workdir}"/bin/${x} || die |
3969 |
+ done |
3970 |
+ fi |
3971 |
+ |
3972 |
+ # Now, set the environment. |
3973 |
+ # But note that ${workdir} may be shared with something else, |
3974 |
+ # and thus already on top of PATH. |
3975 |
+ if [[ ${PATH##:*} != ${workdir}/bin ]]; then |
3976 |
+ PATH=${workdir}/bin${PATH:+:${PATH}} |
3977 |
+ fi |
3978 |
+ if [[ ${PKG_CONFIG_PATH##:*} != ${workdir}/pkgconfig ]]; then |
3979 |
+ PKG_CONFIG_PATH=${workdir}/pkgconfig${PKG_CONFIG_PATH:+:${PKG_CONFIG_PATH}} |
3980 |
+ fi |
3981 |
+ export PATH PKG_CONFIG_PATH |
3982 |
+} |
3983 |
+ |
3984 |
+# @FUNCTION: python_is_python3 |
3985 |
+# @USAGE: [<impl>] |
3986 |
+# @DESCRIPTION: |
3987 |
+# Check whether <impl> (or ${EPYTHON}) is a Python3k variant |
3988 |
+# (i.e. uses syntax and stdlib of Python 3.*). |
3989 |
+# |
3990 |
+# Returns 0 (true) if it is, 1 (false) otherwise. |
3991 |
+python_is_python3() { |
3992 |
+ local impl=${1:-${EPYTHON}} |
3993 |
+ [[ ${impl} ]] || die "python_is_python3: no impl nor EPYTHON" |
3994 |
+ |
3995 |
+ [[ ${impl} == python3* || ${impl} == pypy3 ]] |
3996 |
+} |
3997 |
+ |
3998 |
+# @FUNCTION: python_is_installed |
3999 |
+# @USAGE: [<impl>] |
4000 |
+# @DESCRIPTION: |
4001 |
+# Check whether the interpreter for <impl> (or ${EPYTHON}) is installed. |
4002 |
+# Uses has_version with a proper dependency string. |
4003 |
+# |
4004 |
+# Returns 0 (true) if it is, 1 (false) otherwise. |
4005 |
+python_is_installed() { |
4006 |
+ local impl=${1:-${EPYTHON}} |
4007 |
+ [[ ${impl} ]] || die "${FUNCNAME}: no impl nor EPYTHON" |
4008 |
+ local hasv_args=() |
4009 |
+ |
4010 |
+ case ${EAPI} in |
4011 |
+ 5|6) |
4012 |
+ hasv_args+=( --host-root ) |
4013 |
+ ;; |
4014 |
+ *) |
4015 |
+ hasv_args+=( -b ) |
4016 |
+ ;; |
4017 |
+ esac |
4018 |
+ |
4019 |
+ case "${impl}" in |
4020 |
+ pypy|pypy3) |
4021 |
+ local append= |
4022 |
+ if [[ ${PYTHON_REQ_USE} ]]; then |
4023 |
+ append=[${PYTHON_REQ_USE}] |
4024 |
+ fi |
4025 |
+ |
4026 |
+ # be happy with just the interpeter, no need for the virtual |
4027 |
+ has_version "${hasv_args[@]}" "dev-python/${impl}${append}" \ |
4028 |
+ || has_version "${hasv_args[@]}" "dev-python/${impl}-bin${append}" |
4029 |
+ ;; |
4030 |
+ *) |
4031 |
+ local PYTHON_PKG_DEP |
4032 |
+ python_export "${impl}" PYTHON_PKG_DEP |
4033 |
+ has_version "${hasv_args[@]}" "${PYTHON_PKG_DEP}" |
4034 |
+ ;; |
4035 |
+ esac |
4036 |
+} |
4037 |
+ |
4038 |
+# @FUNCTION: python_fix_shebang |
4039 |
+# @USAGE: [-f|--force] [-q|--quiet] <path>... |
4040 |
+# @DESCRIPTION: |
4041 |
+# Replace the shebang in Python scripts with the current Python |
4042 |
+# implementation (EPYTHON). If a directory is passed, works recursively |
4043 |
+# on all Python scripts. |
4044 |
+# |
4045 |
+# Only files having a 'python*' shebang will be modified. Files with |
4046 |
+# other shebang will either be skipped when working recursively |
4047 |
+# on a directory or treated as error when specified explicitly. |
4048 |
+# |
4049 |
+# Shebangs matching explicitly current Python version will be left |
4050 |
+# unmodified. Shebangs requesting another Python version will be treated |
4051 |
+# as fatal error, unless --force is given. |
4052 |
+# |
4053 |
+# --force causes the function to replace even shebangs that require |
4054 |
+# incompatible Python version. --quiet causes the function not to list |
4055 |
+# modified files verbosely. |
4056 |
+python_fix_shebang() { |
4057 |
+ debug-print-function ${FUNCNAME} "${@}" |
4058 |
+ |
4059 |
+ [[ ${EPYTHON} ]] || die "${FUNCNAME}: EPYTHON unset (pkg_setup not called?)" |
4060 |
+ |
4061 |
+ local force quiet |
4062 |
+ while [[ ${@} ]]; do |
4063 |
+ case "${1}" in |
4064 |
+ -f|--force) force=1; shift;; |
4065 |
+ -q|--quiet) quiet=1; shift;; |
4066 |
+ --) shift; break;; |
4067 |
+ *) break;; |
4068 |
+ esac |
4069 |
+ done |
4070 |
+ |
4071 |
+ [[ ${1} ]] || die "${FUNCNAME}: no paths given" |
4072 |
+ |
4073 |
+ local path f |
4074 |
+ for path; do |
4075 |
+ local any_correct any_fixed is_recursive |
4076 |
+ |
4077 |
+ [[ -d ${path} ]] && is_recursive=1 |
4078 |
+ |
4079 |
+ while IFS= read -r -d '' f; do |
4080 |
+ local shebang i |
4081 |
+ local error= from= |
4082 |
+ |
4083 |
+ # note: we can't ||die here since read will fail if file |
4084 |
+ # has no newline characters |
4085 |
+ IFS= read -r shebang <"${f}" |
4086 |
+ |
4087 |
+ # First, check if it's shebang at all... |
4088 |
+ if [[ ${shebang} == '#!'* ]]; then |
4089 |
+ local split_shebang=() |
4090 |
+ read -r -a split_shebang <<<${shebang} || die |
4091 |
+ |
4092 |
+ # Match left-to-right in a loop, to avoid matching random |
4093 |
+ # repetitions like 'python2.7 python2'. |
4094 |
+ for i in "${split_shebang[@]}"; do |
4095 |
+ case "${i}" in |
4096 |
+ *"${EPYTHON}") |
4097 |
+ debug-print "${FUNCNAME}: in file ${f#${D%/}}" |
4098 |
+ debug-print "${FUNCNAME}: shebang matches EPYTHON: ${shebang}" |
4099 |
+ |
4100 |
+ # Nothing to do, move along. |
4101 |
+ any_correct=1 |
4102 |
+ from=${EPYTHON} |
4103 |
+ break |
4104 |
+ ;; |
4105 |
+ *python|*python[23]) |
4106 |
+ debug-print "${FUNCNAME}: in file ${f#${D%/}}" |
4107 |
+ debug-print "${FUNCNAME}: rewriting shebang: ${shebang}" |
4108 |
+ |
4109 |
+ if [[ ${i} == *python2 ]]; then |
4110 |
+ from=python2 |
4111 |
+ if [[ ! ${force} ]]; then |
4112 |
+ python_is_python3 "${EPYTHON}" && error=1 |
4113 |
+ fi |
4114 |
+ elif [[ ${i} == *python3 ]]; then |
4115 |
+ from=python3 |
4116 |
+ if [[ ! ${force} ]]; then |
4117 |
+ python_is_python3 "${EPYTHON}" || error=1 |
4118 |
+ fi |
4119 |
+ else |
4120 |
+ from=python |
4121 |
+ fi |
4122 |
+ break |
4123 |
+ ;; |
4124 |
+ *python[23].[0123456789]|*pypy|*pypy3|*jython[23].[0123456789]) |
4125 |
+ # Explicit mismatch. |
4126 |
+ if [[ ! ${force} ]]; then |
4127 |
+ error=1 |
4128 |
+ else |
4129 |
+ case "${i}" in |
4130 |
+ *python[23].[0123456789]) |
4131 |
+ from="python[23].[0123456789]";; |
4132 |
+ *pypy) |
4133 |
+ from="pypy";; |
4134 |
+ *pypy3) |
4135 |
+ from="pypy3";; |
4136 |
+ *jython[23].[0123456789]) |
4137 |
+ from="jython[23].[0123456789]";; |
4138 |
+ *) |
4139 |
+ die "${FUNCNAME}: internal error in 2nd pattern match";; |
4140 |
+ esac |
4141 |
+ fi |
4142 |
+ break |
4143 |
+ ;; |
4144 |
+ esac |
4145 |
+ done |
4146 |
+ fi |
4147 |
+ |
4148 |
+ if [[ ! ${error} && ! ${from} ]]; then |
4149 |
+ # Non-Python shebang. Allowed in recursive mode, |
4150 |
+ # disallowed when specifying file explicitly. |
4151 |
+ [[ ${is_recursive} ]] && continue |
4152 |
+ error=1 |
4153 |
+ fi |
4154 |
+ |
4155 |
+ if [[ ! ${quiet} ]]; then |
4156 |
+ einfo "Fixing shebang in ${f#${D%/}}." |
4157 |
+ fi |
4158 |
+ |
4159 |
+ if [[ ! ${error} ]]; then |
4160 |
+ # We either want to match ${from} followed by space |
4161 |
+ # or at end-of-string. |
4162 |
+ if [[ ${shebang} == *${from}" "* ]]; then |
4163 |
+ sed -i -e "1s:${from} :${EPYTHON} :" "${f}" || die |
4164 |
+ else |
4165 |
+ sed -i -e "1s:${from}$:${EPYTHON}:" "${f}" || die |
4166 |
+ fi |
4167 |
+ any_fixed=1 |
4168 |
+ else |
4169 |
+ eerror "The file has incompatible shebang:" |
4170 |
+ eerror " file: ${f#${D%/}}" |
4171 |
+ eerror " current shebang: ${shebang}" |
4172 |
+ eerror " requested impl: ${EPYTHON}" |
4173 |
+ die "${FUNCNAME}: conversion of incompatible shebang requested" |
4174 |
+ fi |
4175 |
+ done < <(find -H "${path}" -type f -print0 || die) |
4176 |
+ |
4177 |
+ if [[ ! ${any_fixed} ]]; then |
4178 |
+ local cmd=eerror |
4179 |
+ [[ ${EAPI} == 5 ]] && cmd=eqawarn |
4180 |
+ |
4181 |
+ "${cmd}" "QA warning: ${FUNCNAME}, ${path#${D%/}} did not match any fixable files." |
4182 |
+ if [[ ${any_correct} ]]; then |
4183 |
+ "${cmd}" "All files have ${EPYTHON} shebang already." |
4184 |
+ else |
4185 |
+ "${cmd}" "There are no Python files in specified directory." |
4186 |
+ fi |
4187 |
+ |
4188 |
+ [[ ${cmd} == eerror ]] && die "${FUNCNAME} did not match any fixable files (QA warning fatal in EAPI ${EAPI})" |
4189 |
+ fi |
4190 |
+ done |
4191 |
+} |
4192 |
+ |
4193 |
+# @FUNCTION: _python_check_locale_sanity |
4194 |
+# @USAGE: <locale> |
4195 |
+# @RETURN: 0 if sane, 1 otherwise |
4196 |
+# @DESCRIPTION: |
4197 |
+# Check whether the specified locale sanely maps between lowercase |
4198 |
+# and uppercase ASCII characters. |
4199 |
+_python_check_locale_sanity() { |
4200 |
+ local -x LC_ALL=${1} |
4201 |
+ local IFS= |
4202 |
+ |
4203 |
+ local lc=( {a..z} ) |
4204 |
+ local uc=( {A..Z} ) |
4205 |
+ local input="${lc[*]}${uc[*]}" |
4206 |
+ |
4207 |
+ local output=$(tr '[:lower:][:upper:]' '[:upper:][:lower:]' <<<"${input}") |
4208 |
+ [[ ${output} == "${uc[*]}${lc[*]}" ]] |
4209 |
+} |
4210 |
+ |
4211 |
+# @FUNCTION: python_export_utf8_locale |
4212 |
+# @RETURN: 0 on success, 1 on failure. |
4213 |
+# @DESCRIPTION: |
4214 |
+# Attempts to export a usable UTF-8 locale in the LC_CTYPE variable. Does |
4215 |
+# nothing if LC_ALL is defined, or if the current locale uses a UTF-8 charmap. |
4216 |
+# This may be used to work around the quirky open() behavior of python3. |
4217 |
+python_export_utf8_locale() { |
4218 |
+ debug-print-function ${FUNCNAME} "${@}" |
4219 |
+ |
4220 |
+ # If the locale program isn't available, just return. |
4221 |
+ type locale >/dev/null || return 0 |
4222 |
+ |
4223 |
+ if [[ $(locale charmap) != UTF-8 ]]; then |
4224 |
+ # Try English first, then everything else. |
4225 |
+ local lang locales="C.UTF-8 en_US.UTF-8 en_GB.UTF-8 $(locale -a)" |
4226 |
+ |
4227 |
+ for lang in ${locales}; do |
4228 |
+ if [[ $(LC_ALL=${lang} locale charmap 2>/dev/null) == UTF-8 ]]; then |
4229 |
+ if _python_check_locale_sanity "${lang}"; then |
4230 |
+ export LC_CTYPE=${lang} |
4231 |
+ if [[ -n ${LC_ALL} ]]; then |
4232 |
+ export LC_NUMERIC=${LC_ALL} |
4233 |
+ export LC_TIME=${LC_ALL} |
4234 |
+ export LC_COLLATE=${LC_ALL} |
4235 |
+ export LC_MONETARY=${LC_ALL} |
4236 |
+ export LC_MESSAGES=${LC_ALL} |
4237 |
+ export LC_PAPER=${LC_ALL} |
4238 |
+ export LC_NAME=${LC_ALL} |
4239 |
+ export LC_ADDRESS=${LC_ALL} |
4240 |
+ export LC_TELEPHONE=${LC_ALL} |
4241 |
+ export LC_MEASUREMENT=${LC_ALL} |
4242 |
+ export LC_IDENTIFICATION=${LC_ALL} |
4243 |
+ export LC_ALL= |
4244 |
+ fi |
4245 |
+ return 0 |
4246 |
+ fi |
4247 |
+ fi |
4248 |
+ done |
4249 |
+ |
4250 |
+ ewarn "Could not find a UTF-8 locale. This may trigger build failures in" |
4251 |
+ ewarn "some python packages. Please ensure that a UTF-8 locale is listed in" |
4252 |
+ ewarn "/etc/locale.gen and run locale-gen." |
4253 |
+ return 1 |
4254 |
+ fi |
4255 |
+ |
4256 |
+ return 0 |
4257 |
+} |
4258 |
+ |
4259 |
+# @FUNCTION: build_sphinx |
4260 |
+# @USAGE: <directory> |
4261 |
+# @DESCRIPTION: |
4262 |
+# Build HTML documentation using dev-python/sphinx in the specified |
4263 |
+# <directory>. Takes care of disabling Intersphinx and appending |
4264 |
+# to HTML_DOCS. |
4265 |
+# |
4266 |
+# If <directory> is relative to the current directory, care needs |
4267 |
+# to be taken to run einstalldocs from the same directory |
4268 |
+# (usually ${S}). |
4269 |
+build_sphinx() { |
4270 |
+ debug-print-function ${FUNCNAME} "${@}" |
4271 |
+ [[ ${#} -eq 1 ]] || die "${FUNCNAME} takes 1 arg: <directory>" |
4272 |
+ |
4273 |
+ local dir=${1} |
4274 |
+ |
4275 |
+ sed -i -e 's:^intersphinx_mapping:disabled_&:' \ |
4276 |
+ "${dir}"/conf.py || die |
4277 |
+ # not all packages include the Makefile in pypi tarball |
4278 |
+ sphinx-build -b html -d "${dir}"/_build/doctrees "${dir}" \ |
4279 |
+ "${dir}"/_build/html || die |
4280 |
+ |
4281 |
+ HTML_DOCS+=( "${dir}/_build/html/." ) |
4282 |
+} |
4283 |
+ |
4284 |
+# -- python.eclass functions -- |
4285 |
+ |
4286 |
+_python_check_dead_variables() { |
4287 |
+ local v |
4288 |
+ |
4289 |
+ for v in PYTHON_DEPEND PYTHON_USE_WITH{,_OR,_OPT} {RESTRICT,SUPPORT}_PYTHON_ABIS |
4290 |
+ do |
4291 |
+ if [[ ${!v} ]]; then |
4292 |
+ die "${v} is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#Ebuild_head" |
4293 |
+ fi |
4294 |
+ done |
4295 |
+ |
4296 |
+ for v in PYTHON_{CPPFLAGS,CFLAGS,CXXFLAGS,LDFLAGS} |
4297 |
+ do |
4298 |
+ if [[ ${!v} ]]; then |
4299 |
+ die "${v} is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#PYTHON_CFLAGS" |
4300 |
+ fi |
4301 |
+ done |
4302 |
+ |
4303 |
+ for v in PYTHON_TESTS_RESTRICTED_ABIS PYTHON_EXPORT_PHASE_FUNCTIONS \ |
4304 |
+ PYTHON_VERSIONED_{SCRIPTS,EXECUTABLES} PYTHON_NONVERSIONED_EXECUTABLES |
4305 |
+ do |
4306 |
+ if [[ ${!v} ]]; then |
4307 |
+ die "${v} is invalid for python-r2 suite" |
4308 |
+ fi |
4309 |
+ done |
4310 |
+ |
4311 |
+ for v in DISTUTILS_USE_SEPARATE_SOURCE_DIRECTORIES DISTUTILS_SETUP_FILES \ |
4312 |
+ DISTUTILS_GLOBAL_OPTIONS DISTUTILS_SRC_TEST PYTHON_MODNAME |
4313 |
+ do |
4314 |
+ if [[ ${!v} ]]; then |
4315 |
+ die "${v} is invalid for distutils-r2, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#${v}" |
4316 |
+ fi |
4317 |
+ done |
4318 |
+ |
4319 |
+ if [[ ${DISTUTILS_DISABLE_TEST_DEPENDENCY} ]]; then |
4320 |
+ die "${v} is invalid for distutils-r2, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#DISTUTILS_SRC_TEST" |
4321 |
+ fi |
4322 |
+ |
4323 |
+ # python.eclass::progress |
4324 |
+ for v in PYTHON_BDEPEND PYTHON_MULTIPLE_ABIS PYTHON_ABI_TYPE \ |
4325 |
+ PYTHON_RESTRICTED_ABIS PYTHON_TESTS_FAILURES_TOLERANT_ABIS \ |
4326 |
+ PYTHON_CFFI_MODULES_GENERATION_COMMANDS |
4327 |
+ do |
4328 |
+ if [[ ${!v} ]]; then |
4329 |
+ die "${v} is invalid for python-r2 suite" |
4330 |
+ fi |
4331 |
+ done |
4332 |
+} |
4333 |
+ |
4334 |
+python_pkg_setup() { |
4335 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#pkg_setup" |
4336 |
+} |
4337 |
+ |
4338 |
+python_convert_shebangs() { |
4339 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#python_convert_shebangs" |
4340 |
+} |
4341 |
+ |
4342 |
+python_clean_py-compile_files() { |
4343 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4344 |
+} |
4345 |
+ |
4346 |
+python_clean_installation_image() { |
4347 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4348 |
+} |
4349 |
+ |
4350 |
+python_execute_function() { |
4351 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#python_execute_function" |
4352 |
+} |
4353 |
+ |
4354 |
+python_generate_wrapper_scripts() { |
4355 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4356 |
+} |
4357 |
+ |
4358 |
+python_merge_intermediate_installation_images() { |
4359 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4360 |
+} |
4361 |
+ |
4362 |
+python_set_active_version() { |
4363 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#pkg_setup" |
4364 |
+} |
4365 |
+ |
4366 |
+python_need_rebuild() { |
4367 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4368 |
+} |
4369 |
+ |
4370 |
+PYTHON() { |
4371 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#.24.28PYTHON.29.2C_.24.7BEPYTHON.7D" |
4372 |
+} |
4373 |
+ |
4374 |
+python_get_implementation() { |
4375 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4376 |
+} |
4377 |
+ |
4378 |
+python_get_implementational_package() { |
4379 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4380 |
+} |
4381 |
+ |
4382 |
+python_get_libdir() { |
4383 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4384 |
+} |
4385 |
+ |
4386 |
+python_get_library() { |
4387 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4388 |
+} |
4389 |
+ |
4390 |
+python_get_version() { |
4391 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4392 |
+} |
4393 |
+ |
4394 |
+python_get_implementation_and_version() { |
4395 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4396 |
+} |
4397 |
+ |
4398 |
+python_execute_nosetests() { |
4399 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4400 |
+} |
4401 |
+ |
4402 |
+python_execute_py.test() { |
4403 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4404 |
+} |
4405 |
+ |
4406 |
+python_execute_trial() { |
4407 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4408 |
+} |
4409 |
+ |
4410 |
+python_enable_pyc() { |
4411 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4412 |
+} |
4413 |
+ |
4414 |
+python_disable_pyc() { |
4415 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4416 |
+} |
4417 |
+ |
4418 |
+python_mod_optimize() { |
4419 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#Python_byte-code_compilation" |
4420 |
+} |
4421 |
+ |
4422 |
+python_mod_cleanup() { |
4423 |
+ die "${FUNCNAME}() is invalid for python-r2 suite, please take a look @ https://wiki.gentoo.org/wiki/Project:Python/Python.eclass_conversion#Python_byte-code_compilation" |
4424 |
+} |
4425 |
+ |
4426 |
+# python.eclass::progress |
4427 |
+ |
4428 |
+python_abi_depend() { |
4429 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4430 |
+} |
4431 |
+ |
4432 |
+python_install_executables() { |
4433 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4434 |
+} |
4435 |
+ |
4436 |
+python_get_extension_module_suffix() { |
4437 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4438 |
+} |
4439 |
+ |
4440 |
+python_byte-compile_modules() { |
4441 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4442 |
+} |
4443 |
+ |
4444 |
+python_clean_byte-compiled_modules() { |
4445 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4446 |
+} |
4447 |
+ |
4448 |
+python_generate_cffi_modules() { |
4449 |
+ die "${FUNCNAME}() is invalid for python-r2 suite" |
4450 |
+} |
4451 |
+ |
4452 |
+_PYTHON_UTILS_R2=1 |
4453 |
+fi |
4454 |
diff --git a/eclass/tests/distutils-r2.sh b/eclass/tests/distutils-r2.sh |
4455 |
new file mode 100755 |
4456 |
index 000000000000..15f59bcd7d48 |
4457 |
--- /dev/null |
4458 |
+++ b/eclass/tests/distutils-r2.sh |
4459 |
@@ -0,0 +1,98 @@ |
4460 |
+#!/bin/bash |
4461 |
+# Copyright 1999-2015 Gentoo Foundation |
4462 |
+# Distributed under the terms of the GNU General Public License v2 |
4463 |
+ |
4464 |
+EAPI=5 |
4465 |
+PYTHON_COMPAT=( python2_7 ) |
4466 |
+source tests-common.sh |
4467 |
+ |
4468 |
+test-phase_name_free() { |
4469 |
+ local ph=${1} |
4470 |
+ |
4471 |
+ if declare -f "${ph}"; then |
4472 |
+ die "${ph} function declared while name reserved for phase!" |
4473 |
+ fi |
4474 |
+ if declare -f "${ph}_all"; then |
4475 |
+ die "${ph}_all function declared while name reserved for phase!" |
4476 |
+ fi |
4477 |
+} |
4478 |
+ |
4479 |
+test-distutils_enable_tests() { |
4480 |
+ local runner=${1} |
4481 |
+ local exp_IUSE=${2} |
4482 |
+ local exp_RESTRICT=${3} |
4483 |
+ local exp_DEPEND=${4} |
4484 |
+ |
4485 |
+ local IUSE=${IUSE} |
4486 |
+ local RESTRICT=${RESTRICT} |
4487 |
+ local DEPEND=${DEPEND} |
4488 |
+ |
4489 |
+ tbegin "${runner}" |
4490 |
+ |
4491 |
+ distutils_enable_tests "${runner}" |
4492 |
+ |
4493 |
+ local ret var |
4494 |
+ for var in IUSE RESTRICT DEPEND; do |
4495 |
+ local exp_var=exp_${var} |
4496 |
+ if [[ ${!var} != "${!exp_var}" ]]; then |
4497 |
+ eindent |
4498 |
+ eerror "${var} expected: ${!exp_var}" |
4499 |
+ eerror "${var} actual: ${!var}" |
4500 |
+ eoutdent |
4501 |
+ ret=1 |
4502 |
+ tret=1 |
4503 |
+ fi |
4504 |
+ done |
4505 |
+ |
4506 |
+ tend ${ret} |
4507 |
+} |
4508 |
+ |
4509 |
+DISTUTILS_USE_SETUPTOOLS=no |
4510 |
+inherit distutils-r2 |
4511 |
+ |
4512 |
+tbegin "sane function names" |
4513 |
+ |
4514 |
+test-phase_name_free python_prepare |
4515 |
+test-phase_name_free python_configure |
4516 |
+test-phase_name_free python_compile |
4517 |
+test-phase_name_free python_test |
4518 |
+test-phase_name_free python_install |
4519 |
+ |
4520 |
+tend |
4521 |
+ |
4522 |
+einfo distutils_enable_tests |
4523 |
+eindent |
4524 |
+BASE_IUSE="python_targets_python2_7" |
4525 |
+BASE_DEPS="python_targets_python2_7? ( >=dev-lang/python-2.7.5-r2:2.7 ) >=dev-lang/python-exec-2:=[python_targets_python2_7(-)?,-python_single_target_python2_7(-)]" |
4526 |
+TEST_RESTRICT=" !test? ( test )" |
4527 |
+ |
4528 |
+einfo "empty RDEPEND" |
4529 |
+eindent |
4530 |
+RDEPEND="" |
4531 |
+test-distutils_enable_tests pytest \ |
4532 |
+ "${BASE_IUSE} test" "${TEST_RESTRICT}" "${BASE_DEPS} test? ( dev-python/pytest[${PYTHON_USEDEP}] )" |
4533 |
+test-distutils_enable_tests nose \ |
4534 |
+ "${BASE_IUSE} test" "${TEST_RESTRICT}" "${BASE_DEPS} test? ( dev-python/nose[${PYTHON_USEDEP}] )" |
4535 |
+test-distutils_enable_tests unittest \ |
4536 |
+ "${BASE_IUSE}" "" "${BASE_DEPS}" |
4537 |
+test-distutils_enable_tests setup.py \ |
4538 |
+ "${BASE_IUSE}" "" "${BASE_DEPS}" |
4539 |
+eoutdent |
4540 |
+ |
4541 |
+einfo "non-empty RDEPEND" |
4542 |
+eindent |
4543 |
+BASE_RDEPEND="dev-python/foo[${PYTHON_USEDEP}]" |
4544 |
+RDEPEND=${BASE_RDEPEND} |
4545 |
+test-distutils_enable_tests pytest \ |
4546 |
+ "${BASE_IUSE} test" "${TEST_RESTRICT}" "${BASE_DEPS} test? ( ${BASE_RDEPEND} dev-python/pytest[${PYTHON_USEDEP}] )" |
4547 |
+test-distutils_enable_tests nose \ |
4548 |
+ "${BASE_IUSE} test" "${TEST_RESTRICT}" "${BASE_DEPS} test? ( ${BASE_RDEPEND} dev-python/nose[${PYTHON_USEDEP}] )" |
4549 |
+test-distutils_enable_tests unittest \ |
4550 |
+ "${BASE_IUSE} test" "${TEST_RESTRICT}" "${BASE_DEPS} test? ( ${BASE_RDEPEND} )" |
4551 |
+test-distutils_enable_tests setup.py \ |
4552 |
+ "${BASE_IUSE} test" "${TEST_RESTRICT}" "${BASE_DEPS} test? ( ${BASE_RDEPEND} )" |
4553 |
+eoutdent |
4554 |
+ |
4555 |
+eoutdent |
4556 |
+ |
4557 |
+texit |
4558 |
diff --git a/eclass/tests/python-utils-r2.sh b/eclass/tests/python-utils-r2.sh |
4559 |
new file mode 100755 |
4560 |
index 000000000000..64490cb0d24a |
4561 |
--- /dev/null |
4562 |
+++ b/eclass/tests/python-utils-r2.sh |
4563 |
@@ -0,0 +1,237 @@ |
4564 |
+#!/bin/bash |
4565 |
+# Copyright 1999-2019 Gentoo Authors |
4566 |
+# Distributed under the terms of the GNU General Public License v2 |
4567 |
+ |
4568 |
+EAPI=7 |
4569 |
+source tests-common.sh |
4570 |
+ |
4571 |
+test_var() { |
4572 |
+ local var=${1} |
4573 |
+ local impl=${2} |
4574 |
+ local expect=${3} |
4575 |
+ |
4576 |
+ tbegin "${var} for ${impl}" |
4577 |
+ |
4578 |
+ local ${var} |
4579 |
+ python_export ${impl} PYTHON ${var} |
4580 |
+ [[ ${!var} == ${expect} ]] || eerror "(${impl}: ${var}: ${!var} != ${expect}" |
4581 |
+ |
4582 |
+ tend ${?} |
4583 |
+} |
4584 |
+ |
4585 |
+test_is() { |
4586 |
+ local func=${1} |
4587 |
+ local expect=${2} |
4588 |
+ |
4589 |
+ tbegin "${func} (expecting: ${expect})" |
4590 |
+ |
4591 |
+ ${func} |
4592 |
+ [[ ${?} == ${expect} ]] |
4593 |
+ |
4594 |
+ tend ${?} |
4595 |
+} |
4596 |
+ |
4597 |
+test_fix_shebang() { |
4598 |
+ local from=${1} |
4599 |
+ local to=${2} |
4600 |
+ local expect=${3} |
4601 |
+ local args=( "${@:4}" ) |
4602 |
+ |
4603 |
+ tbegin "python_fix_shebang${args[@]+ ${args[*]}} from ${from} to ${to} (exp: ${expect})" |
4604 |
+ |
4605 |
+ echo "${from}" > "${tmpfile}" |
4606 |
+ output=$( EPYTHON=${to} python_fix_shebang "${args[@]}" -q "${tmpfile}" 2>&1 ) |
4607 |
+ |
4608 |
+ if [[ ${?} != 0 ]]; then |
4609 |
+ if [[ ${expect} != FAIL ]]; then |
4610 |
+ echo "${output}" |
4611 |
+ tend 1 |
4612 |
+ else |
4613 |
+ tend 0 |
4614 |
+ fi |
4615 |
+ else |
4616 |
+ [[ $(<"${tmpfile}") == ${expect} ]] \ |
4617 |
+ || eerror "${from} -> ${to}: $(<"${tmpfile}") != ${expect}" |
4618 |
+ tend ${?} |
4619 |
+ fi |
4620 |
+} |
4621 |
+ |
4622 |
+tmpfile=$(mktemp) |
4623 |
+ |
4624 |
+inherit python-utils-r2 |
4625 |
+ |
4626 |
+test_var EPYTHON python2_7 python2.7 |
4627 |
+test_var PYTHON python2_7 /usr/bin/python2.7 |
4628 |
+if [[ -x /usr/bin/python2.7 ]]; then |
4629 |
+ test_var PYTHON_SITEDIR python2_7 "/usr/lib*/python2.7/site-packages" |
4630 |
+ test_var PYTHON_INCLUDEDIR python2_7 /usr/include/python2.7 |
4631 |
+ test_var PYTHON_LIBPATH python2_7 "/usr/lib*/libpython2.7$(get_libname)" |
4632 |
+ test_var PYTHON_CONFIG python2_7 /usr/bin/python2.7-config |
4633 |
+ test_var PYTHON_CFLAGS python2_7 "*-I/usr/include/python2.7*" |
4634 |
+ test_var PYTHON_LIBS python2_7 "*-lpython2.7*" |
4635 |
+fi |
4636 |
+test_var PYTHON_PKG_DEP python2_7 '*dev-lang/python*:2.7' |
4637 |
+test_var PYTHON_SCRIPTDIR python2_7 /usr/lib/python-exec/python2.7 |
4638 |
+ |
4639 |
+test_var EPYTHON python3_6 python3.6 |
4640 |
+test_var PYTHON python3_6 /usr/bin/python3.6 |
4641 |
+if [[ -x /usr/bin/python3.6 ]]; then |
4642 |
+ abiflags=$(/usr/bin/python3.6 -c 'import sysconfig; print(sysconfig.get_config_var("ABIFLAGS"))') |
4643 |
+ test_var PYTHON_SITEDIR python3_6 "/usr/lib*/python3.6/site-packages" |
4644 |
+ test_var PYTHON_INCLUDEDIR python3_6 "/usr/include/python3.6${abiflags}" |
4645 |
+ test_var PYTHON_LIBPATH python3_6 "/usr/lib*/libpython3.6${abiflags}$(get_libname)" |
4646 |
+ test_var PYTHON_CONFIG python3_6 "/usr/bin/python3.6${abiflags}-config" |
4647 |
+ test_var PYTHON_CFLAGS python3_6 "*-I/usr/include/python3.6*" |
4648 |
+ test_var PYTHON_LIBS python3_6 "*-lpython3.6*" |
4649 |
+fi |
4650 |
+test_var PYTHON_PKG_DEP python3_6 '*dev-lang/python*:3.6' |
4651 |
+test_var PYTHON_SCRIPTDIR python3_6 /usr/lib/python-exec/python3.6 |
4652 |
+ |
4653 |
+test_var EPYTHON python3_7 python3.7 |
4654 |
+test_var PYTHON python3_7 /usr/bin/python3.7 |
4655 |
+if [[ -x /usr/bin/python3.7 ]]; then |
4656 |
+ abiflags=$(/usr/bin/python3.7 -c 'import sysconfig; print(sysconfig.get_config_var("ABIFLAGS"))') |
4657 |
+ test_var PYTHON_SITEDIR python3_7 "/usr/lib/python3.7/site-packages" |
4658 |
+ test_var PYTHON_INCLUDEDIR python3_7 "/usr/include/python3.7${abiflags}" |
4659 |
+ test_var PYTHON_LIBPATH python3_7 "/usr/lib*/libpython3.7${abiflags}$(get_libname)" |
4660 |
+ test_var PYTHON_CONFIG python3_7 "/usr/bin/python3.7${abiflags}-config" |
4661 |
+ test_var PYTHON_CFLAGS python3_7 "*-I/usr/include/python3.7*" |
4662 |
+ test_var PYTHON_LIBS python3_7 "*-lpython3.7*" |
4663 |
+fi |
4664 |
+test_var PYTHON_PKG_DEP python3_7 '*dev-lang/python*:3.7' |
4665 |
+test_var PYTHON_SCRIPTDIR python3_7 /usr/lib/python-exec/python3.7 |
4666 |
+ |
4667 |
+test_var EPYTHON jython2_7 jython2.7 |
4668 |
+test_var PYTHON jython2_7 /usr/bin/jython2.7 |
4669 |
+if [[ -x /usr/bin/jython2.7 ]]; then |
4670 |
+ test_var PYTHON_SITEDIR jython2_7 /usr/share/jython-2.7/Lib/site-packages |
4671 |
+fi |
4672 |
+test_var PYTHON_PKG_DEP jython2_7 '*dev-java/jython*:2.7' |
4673 |
+test_var PYTHON_SCRIPTDIR jython2_7 /usr/lib/python-exec/jython2.7 |
4674 |
+ |
4675 |
+test_var EPYTHON pypy pypy |
4676 |
+test_var PYTHON pypy /usr/bin/pypy |
4677 |
+if [[ -x /usr/bin/pypy ]]; then |
4678 |
+ test_var PYTHON_SITEDIR pypy "/usr/lib*/pypy2.7/site-packages" |
4679 |
+ test_var PYTHON_INCLUDEDIR pypy "/usr/lib*/pypy2.7/include" |
4680 |
+fi |
4681 |
+test_var PYTHON_PKG_DEP pypy '*dev-python/pypy*:0=' |
4682 |
+test_var PYTHON_SCRIPTDIR pypy /usr/lib/python-exec/pypy |
4683 |
+ |
4684 |
+test_var EPYTHON pypy3 pypy3 |
4685 |
+test_var PYTHON pypy3 /usr/bin/pypy3 |
4686 |
+if [[ -x /usr/bin/pypy3 ]]; then |
4687 |
+ test_var PYTHON_SITEDIR pypy3 "/usr/lib*/pypy3.?/site-packages" |
4688 |
+ test_var PYTHON_INCLUDEDIR pypy3 "/usr/lib*/pypy3.?/include" |
4689 |
+fi |
4690 |
+test_var PYTHON_PKG_DEP pypy3 '*dev-python/pypy3*:0=' |
4691 |
+test_var PYTHON_SCRIPTDIR pypy3 /usr/lib/python-exec/pypy3 |
4692 |
+ |
4693 |
+test_is "python_is_python3 python2.7" 1 |
4694 |
+test_is "python_is_python3 python3.2" 0 |
4695 |
+test_is "python_is_python3 jython2.7" 1 |
4696 |
+test_is "python_is_python3 pypy" 1 |
4697 |
+test_is "python_is_python3 pypy3" 0 |
4698 |
+ |
4699 |
+# generic shebangs |
4700 |
+test_fix_shebang '#!/usr/bin/python' python2.7 '#!/usr/bin/python2.7' |
4701 |
+test_fix_shebang '#!/usr/bin/python' python3.6 '#!/usr/bin/python3.6' |
4702 |
+test_fix_shebang '#!/usr/bin/python' pypy '#!/usr/bin/pypy' |
4703 |
+test_fix_shebang '#!/usr/bin/python' pypy3 '#!/usr/bin/pypy3' |
4704 |
+test_fix_shebang '#!/usr/bin/python' jython2.7 '#!/usr/bin/jython2.7' |
4705 |
+ |
4706 |
+# python2/python3 matching |
4707 |
+test_fix_shebang '#!/usr/bin/python2' python2.7 '#!/usr/bin/python2.7' |
4708 |
+test_fix_shebang '#!/usr/bin/python3' python2.7 FAIL |
4709 |
+test_fix_shebang '#!/usr/bin/python3' python2.7 '#!/usr/bin/python2.7' --force |
4710 |
+test_fix_shebang '#!/usr/bin/python3' python3.6 '#!/usr/bin/python3.6' |
4711 |
+test_fix_shebang '#!/usr/bin/python2' python3.6 FAIL |
4712 |
+test_fix_shebang '#!/usr/bin/python2' python3.6 '#!/usr/bin/python3.6' --force |
4713 |
+ |
4714 |
+# pythonX.Y matching (those mostly test the patterns) |
4715 |
+test_fix_shebang '#!/usr/bin/python2.7' python2.7 '#!/usr/bin/python2.7' |
4716 |
+test_fix_shebang '#!/usr/bin/python2.7' python3.2 FAIL |
4717 |
+test_fix_shebang '#!/usr/bin/python2.7' python3.2 '#!/usr/bin/python3.2' --force |
4718 |
+test_fix_shebang '#!/usr/bin/python3.2' python3.2 '#!/usr/bin/python3.2' |
4719 |
+test_fix_shebang '#!/usr/bin/python3.2' python2.7 FAIL |
4720 |
+test_fix_shebang '#!/usr/bin/python3.2' python2.7 '#!/usr/bin/python2.7' --force |
4721 |
+test_fix_shebang '#!/usr/bin/pypy' pypy '#!/usr/bin/pypy' |
4722 |
+test_fix_shebang '#!/usr/bin/pypy' python2.7 FAIL |
4723 |
+test_fix_shebang '#!/usr/bin/pypy' python2.7 '#!/usr/bin/python2.7' --force |
4724 |
+test_fix_shebang '#!/usr/bin/jython2.7' jython2.7 '#!/usr/bin/jython2.7' |
4725 |
+test_fix_shebang '#!/usr/bin/jython2.7' jython3.2 FAIL |
4726 |
+test_fix_shebang '#!/usr/bin/jython2.7' jython3.2 '#!/usr/bin/jython3.2' --force |
4727 |
+ |
4728 |
+# fancy path handling |
4729 |
+test_fix_shebang '#!/mnt/python2/usr/bin/python' python3.6 \ |
4730 |
+ '#!/mnt/python2/usr/bin/python3.6' |
4731 |
+test_fix_shebang '#!/mnt/python2/usr/bin/python2' python2.7 \ |
4732 |
+ '#!/mnt/python2/usr/bin/python2.7' |
4733 |
+test_fix_shebang '#!/mnt/python2/usr/bin/env python' python2.7 \ |
4734 |
+ '#!/mnt/python2/usr/bin/env python2.7' |
4735 |
+test_fix_shebang '#!/mnt/python2/usr/bin/python2 python2' python2.7 \ |
4736 |
+ '#!/mnt/python2/usr/bin/python2.7 python2' |
4737 |
+test_fix_shebang '#!/mnt/python2/usr/bin/python3 python2' python2.7 FAIL |
4738 |
+test_fix_shebang '#!/mnt/python2/usr/bin/python3 python2' python2.7 \ |
4739 |
+ '#!/mnt/python2/usr/bin/python2.7 python2' --force |
4740 |
+test_fix_shebang '#!/usr/bin/foo' python2.7 FAIL |
4741 |
+ |
4742 |
+# regression test for bug #522080 |
4743 |
+test_fix_shebang '#!/usr/bin/python ' python2.7 '#!/usr/bin/python2.7 ' |
4744 |
+ |
4745 |
+# make sure we don't break pattern matching |
4746 |
+test_is "_python_impl_supported python2_5" 1 |
4747 |
+test_is "_python_impl_supported python2_6" 1 |
4748 |
+test_is "_python_impl_supported python2_7" 0 |
4749 |
+test_is "_python_impl_supported python3_1" 1 |
4750 |
+test_is "_python_impl_supported python3_2" 1 |
4751 |
+test_is "_python_impl_supported python3_3" 1 |
4752 |
+test_is "_python_impl_supported python3_4" 1 |
4753 |
+test_is "_python_impl_supported python3_5" 1 |
4754 |
+test_is "_python_impl_supported python3_6" 0 |
4755 |
+test_is "_python_impl_supported python3_7" 0 |
4756 |
+test_is "_python_impl_supported python3_8" 0 |
4757 |
+test_is "_python_impl_supported pypy1_8" 1 |
4758 |
+test_is "_python_impl_supported pypy1_9" 1 |
4759 |
+test_is "_python_impl_supported pypy2_0" 1 |
4760 |
+test_is "_python_impl_supported pypy" 1 |
4761 |
+test_is "_python_impl_supported pypy3" 0 |
4762 |
+test_is "_python_impl_supported jython2_7" 1 |
4763 |
+ |
4764 |
+# check _python_impl_matches behavior |
4765 |
+test_is "_python_impl_matches python2_7 -2" 0 |
4766 |
+test_is "_python_impl_matches python3_6 -2" 1 |
4767 |
+test_is "_python_impl_matches python3_7 -2" 1 |
4768 |
+test_is "_python_impl_matches pypy -2" 0 |
4769 |
+test_is "_python_impl_matches pypy3 -2" 1 |
4770 |
+test_is "_python_impl_matches python2_7 -3" 1 |
4771 |
+test_is "_python_impl_matches python3_6 -3" 0 |
4772 |
+test_is "_python_impl_matches python3_7 -3" 0 |
4773 |
+test_is "_python_impl_matches pypy -3" 1 |
4774 |
+test_is "_python_impl_matches pypy3 -3" 0 |
4775 |
+test_is "_python_impl_matches python2_7 -2 python3_6" 0 |
4776 |
+test_is "_python_impl_matches python3_6 -2 python3_6" 0 |
4777 |
+test_is "_python_impl_matches python3_7 -2 python3_6" 1 |
4778 |
+test_is "_python_impl_matches pypy -2 python3_6" 0 |
4779 |
+test_is "_python_impl_matches pypy3 -2 python3_6" 1 |
4780 |
+test_is "_python_impl_matches python2_7 pypy3 -2 python3_6" 0 |
4781 |
+test_is "_python_impl_matches python3_6 pypy3 -2 python3_6" 0 |
4782 |
+test_is "_python_impl_matches python3_7 pypy3 -2 python3_6" 1 |
4783 |
+test_is "_python_impl_matches pypy pypy3 -2 python3_6" 0 |
4784 |
+test_is "_python_impl_matches pypy3 pypy3 -2 python3_6" 0 |
4785 |
+set -f |
4786 |
+test_is "_python_impl_matches python2_7 pypy*" 1 |
4787 |
+test_is "_python_impl_matches python3_6 pypy*" 1 |
4788 |
+test_is "_python_impl_matches python3_7 pypy*" 1 |
4789 |
+test_is "_python_impl_matches pypy pypy*" 0 |
4790 |
+test_is "_python_impl_matches pypy3 pypy*" 0 |
4791 |
+test_is "_python_impl_matches python2_7 python*" 0 |
4792 |
+test_is "_python_impl_matches python3_6 python*" 0 |
4793 |
+test_is "_python_impl_matches python3_7 python*" 0 |
4794 |
+test_is "_python_impl_matches pypy python*" 1 |
4795 |
+test_is "_python_impl_matches pypy3 python*" 1 |
4796 |
+set +f |
4797 |
+ |
4798 |
+rm "${tmpfile}" |
4799 |
+ |
4800 |
+texit |
4801 |
-- |
4802 |
2.25.1 |