File: setup.py

package info (click to toggle)
cysignals 1.3.2%2Bds-1
  • links: PTS, VCS
  • area: main
  • in suites: stretch
  • size: 504 kB
  • sloc: ansic: 485; python: 442; makefile: 300; sh: 41
file content (188 lines) | stat: -rwxr-xr-x 6,455 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from distutils.core import setup, Distribution
from distutils.command.build_py import build_py as _build_py
from distutils.command.build_ext import build_ext as _build_ext
from distutils.extension import Extension
from Cython.Build.Dependencies import cythonize

import warnings
warnings.simplefilter("always")

import os
from glob import glob

import sys

opj = os.path.join

ac_configure_flags = os.environ.get("PYSETUP_CONFIGURE_FLAGS","--without-pari")
if "--without-pari" in sys.argv:
	ac_configure_flags = "--without-pari"
	sys.argv.remove("--without-pari")
if "--with-pari" in sys.argv:
	ac_configure_flags = "--with-pari"
	sys.argv.remove("--with-pari")

env_PYBUILD_DESTDIR = os.environ.get("PYBUILD_DESTDIR")

cythonize_dir = "build/XXXX"
if "--without-pari" in ac_configure_flags:
	cythonize_dir = "build/bare"
elif "--with-pari" in ac_configure_flags:
	cythonize_dir = "build/pari"

kwds = dict(include_dirs=[opj("src", "cysignals"),
                          opj(cythonize_dir, "src"),
                          opj(cythonize_dir, "src", "cysignals")],
            depends=glob(opj("src", "cysignals", "*.h")))

extensions = [
    Extension("cysignals.signals", ["src/cysignals/signals.pyx"], **kwds),
    Extension("cysignals.alarm", ["src/cysignals/alarm.pyx"], **kwds),
    Extension("cysignals.pselect", ["src/cysignals/pselect.pyx"], **kwds),
    Extension("cysignals.tests", ["src/cysignals/tests.pyx"], **kwds),
]


def write_if_changed(filename, text):
    """
    Write ``text`` to ``filename`` but only if it differs from the
    current content of ``filename``. If needed, the file and the
    containing directory are created.
    """
    try:
        f = open(filename, "r+")
    except IOError:
        try:
            os.makedirs(os.path.dirname(filename))
        except OSError:
            pass
        f = open(filename, "w")
    else:
        if f.read() == text:
            # File is up-to-date
            f.close()
            return
        f.seek(0)
        f.truncate()

    print("generating {0}".format(filename))
    f.write(text)
    f.close()


# Run Distutils
class build_py(_build_py):
    """
    Custom distutils build_py class. For every package FOO, we also
    check package data for a "fake" FOO-cython package.
    """
    def get_data_files(self):
        """Generate list of '(package,src_dir,build_dir,filenames)' tuples"""
        data = []
        if not self.packages:
            return data
        for package in self.packages:
            for src_package in [package, package + "-cython"]:
                # Locate package source directory
                src_dir = self.get_package_dir(src_package)

                # Compute package build directory
                build_dir = os.path.join(*([self.build_lib] + package.split('.')))

                # Length of path to strip from found files
                plen = 0
                if src_dir:
                    plen = len(src_dir)+1

                # Strip directory from globbed filenames
                filenames = [
                    file[plen:] for file in self.find_data_files(src_package, src_dir)
                    ]
                data.append((package, src_dir, build_dir, filenames))
        return data


class build_ext(_build_ext):
    def finalize_options(self):
        _build_ext.finalize_options(self)
        self.create_init_pxd()
        ext_modules = self.distribution.ext_modules
        if ext_modules:
            self.distribution.ext_modules[:] = self.cythonize(ext_modules)

    def cythonize(self, extensions):
        return cythonize(extensions,
                build_dir=cythonize_dir, include_path=["src", os.path.join(cythonize_dir, "src")])

    def create_init_pxd(self):
        """
        Create an ``__init__.pxd`` file in the build directory. This
        file will then be installed.

        The ``__init__.pxd`` file sets the correct compiler options for
        packages using cysignals.
        """
        dist = self.distribution

        # Determine installation directory
        inst = dist.get_command_obj("install")
        inst.ensure_finalized()
        install_dir = opj(inst.install_platlib, "cysignals")

        # The variable "init_pxd" is the string which should be written to
        # __init__.pxd
        init_pxd = "# distutils: include_dirs = {0}\n".format(install_dir)

        if env_PYBUILD_DESTDIR is None:
            # Append __init__.pxd from configure
            init_pxd += self.get_init_pxd()
        else:
            init_pxd = init_pxd.replace(env_PYBUILD_DESTDIR,"")

        init_pxd_file = opj(self.build_lib, "cysignals", "__init__.pxd")
        write_if_changed(init_pxd_file, init_pxd)

    def get_init_pxd(self):
        """
        Get the contents of ``__init__.pxd`` as generated by configure.
        """
        configure_init_pxd_file = opj(cythonize_dir, "src", "cysignals", "__init__.pxd")
        # Run configure if needed
        try:
            f = open(configure_init_pxd_file, "r")
        except IOError:
            import subprocess
            subprocess.check_call(
                "make configure && mkdir -p " + cythonize_dir +
                " && " +
                "{ cd " + cythonize_dir + " ; ../../configure " + ac_configure_flags + " ; }" ,
              shell=True)
            f = open(configure_init_pxd_file, "r")
        with f:
            return f.read()


setup(
    name="cysignals",
    author=u"Martin R. Albrecht, François Bissey, Volker Braun, Jeroen Demeyer",
    author_email="sage-devel@googlegroups.com",
    version=open("VERSION").read().strip(),
    url="https://github.com/sagemath/cysignals",
    license="GNU Lesser General Public License, version 3 or later",
    description="Interrupt and signal handling for Cython",
    long_description=open('README.rst').read(),
    platforms=["POSIX"],

    ext_modules=extensions,
    packages=["cysignals","cysignals_gdb"],
    package_dir={"cysignals": opj("src", "cysignals"),
                 "cysignals-cython": opj(cythonize_dir, "src", "cysignals"),
                 "cysignals_gdb": opj("src", "scripts")},
    package_data={"cysignals": ["*.pxi", "*.pxd", "*.h"],
                  "cysignals-cython": ["*.h"],
                  "cysignals_gdb": ["cysignals-CSI-helper.py"]},
    scripts=[opj("src", "scripts", "cysignals-CSI")],
    cmdclass=dict(build_py=build_py, build_ext=build_ext),
)