|
From: <th...@us...> - 2017-01-04 15:34:10
|
Revision: 766
http://sourceforge.net/p/py2exe/svn/766
Author: theller
Date: 2017-01-04 15:34:08 +0000 (Wed, 04 Jan 2017)
Log Message:
-----------
Updates from upstream version.
Modified Paths:
--------------
trunk/py2exe-3/py2exe/__init__.py
trunk/py2exe-3/py2exe/boot_ctypes_com_server.py
trunk/py2exe-3/py2exe/distutils_buildexe.py
trunk/py2exe-3/py2exe/dllfinder.py
trunk/py2exe-3/py2exe/hooks.py
trunk/py2exe-3/py2exe/mf3.py
trunk/py2exe-3/py2exe/mf34.py
trunk/py2exe-3/py2exe/py2exe_distutils.py
trunk/py2exe-3/py2exe/runtime.py
trunk/py2exe-3/setup.py
trunk/py2exe-3/source/MyLoadLibrary.c
trunk/py2exe-3/source/Python-dynload.h
trunk/py2exe-3/source/_memimporter.c
trunk/py2exe-3/source/python-dynload.c
trunk/py2exe-3/source/run_ctypes_dll.c
trunk/py2exe-3/zipextimporter.py
Modified: trunk/py2exe-3/py2exe/__init__.py
===================================================================
--- trunk/py2exe-3/py2exe/__init__.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/__init__.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -2,7 +2,7 @@
# -*- coding: utf-8 -*-
"""py2exe package
"""
-__version__ = "0.9.2.2"
+__version__ = "0.9.2.5"
from .patch_distutils import patch_distutils
Modified: trunk/py2exe-3/py2exe/boot_ctypes_com_server.py
===================================================================
--- trunk/py2exe-3/py2exe/boot_ctypes_com_server.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/boot_ctypes_com_server.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -66,6 +66,7 @@
# dump each class
for cls in get_classes(mod):
classmap[cls._reg_clsid_] = cls
+ #print("build_class_map: ",classmap)
import comtypes.server.inprocserver
comtypes.server.inprocserver._clsid_to_class = classmap
build_class_map()
Modified: trunk/py2exe-3/py2exe/distutils_buildexe.py
===================================================================
--- trunk/py2exe-3/py2exe/distutils_buildexe.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/distutils_buildexe.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -130,9 +130,12 @@
('custom-boot-script=', None,
"Python file that will be run when setting up the runtime environment"),
+
+ ('use-assembly', None,
+ "use windows assembly to isolate python dll in ctypes-com-server."),
]
- boolean_options = ["compressed", "xref", "ascii", "skip-archive"]
+ boolean_options = ["compressed", "xref", "ascii", "skip-archive","use-assembly"]
def initialize_options (self):
self.xref =0
@@ -150,6 +153,7 @@
self.skip_archive = 0
self.ascii = 0
self.custom_boot_script = None
+ self.use_assembly = False
def finalize_options (self):
self.optimize = int(self.optimize)
@@ -258,11 +262,12 @@
data_files = self.distribution.data_files,
compress = self.compressed,
+ use_assembly = self.use_assembly,
)
## level = logging.INFO if options.verbose else logging.WARNING
## logging.basicConfig(level=level)
-
+ #import pdb;pdb.set_trace()
builder = runtime.Runtime(options)
builder.analyze()
builder.build()
Modified: trunk/py2exe-3/py2exe/dllfinder.py
===================================================================
--- trunk/py2exe-3/py2exe/dllfinder.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/dllfinder.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -84,9 +84,18 @@
"""Call BindImageEx and collect all dlls that are bound.
"""
# XXX Should cache results!
+ import platform
+ if platform.architecture()[0]=="32bit":
+ pth = ";".join([p for p in os.environ["PATH"].split(';') if not "intel64_win" in p])
+ elif platform.architecture()[0]=="64bit":
+ pth = ";".join([p for p in os.environ["PATH"].split(';') if not "ia32_win" in p])
+ else:
+ pth = os.environ["PATH"]
+
+ #import pdb;pdb.set_trace()
path = ";".join([os.path.dirname(imagename),
os.path.dirname(sys.executable),
- os.environ["PATH"]])
+ pth])
result = set()
@_wapi.PIMAGEHLP_STATUS_ROUTINE
@@ -278,4 +287,4 @@
scanner = Scanner()
scanner.import_package("numpy")
- scanner.report_dlls()
+ print(scanner.all_dlls())
Modified: trunk/py2exe-3/py2exe/hooks.py
===================================================================
--- trunk/py2exe-3/py2exe/hooks.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/hooks.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -326,6 +326,7 @@
finder.ignore("nose")
finder.ignore("scipy")
+
def hook_nose(finder, module):
finder.ignore("IronPython")
finder.ignore("cStringIO")
@@ -481,3 +482,45 @@
def hook_numpy_core(finder, module):
finder.ignore("numpy.core._dotblas")
+ numpy_core_path = os.path.dirname(module.__loader__.path)
+ #add mkl dlls from numpy.core, if present
+ from os import listdir
+ dlls = [os.path.join(numpy_core_path,mkl) for mkl in listdir(numpy_core_path) if mkl.startswith('mkl_')]
+ for dll in dlls:
+ finder.add_dll(dll)
+
+
+def hook_scipy_special(finder, module):
+ #import pdb;pdb.set_trace()
+ depth = getattr(finder,"recursion_depth_special",0)
+ if depth==0:
+ finder.recursion_depth_special = depth + 1
+ finder.import_hook("scipy.special._ufuncs_cxx")
+ finder.import_hook("scipy.special.orthogonal")
+ finder.import_hook("scipy", fromlist=("linalg",))
+ finder.recursion_depth_special = depth
+
+def hook_scipy_linalg(finder, module):
+ depth = getattr(finder,"recursion_depth_linalg",0)
+ if depth==0:
+ finder.recursion_depth_linalg = depth + 1
+ finder.import_hook("scipy.linalg.cython_blas")
+ finder.import_hook("scipy.linalg.cython_lapack")
+ finder.import_hook("scipy.integrate")
+ finder.recursion_depth_linalg = depth
+
+
+def hook_scipy_sparse_csgraph(finder, module):
+ depth = getattr(finder,"recursion_depth_sparse",0)
+ if depth==0:
+ finder.recursion_depth_sparse = depth + 1
+ finder.import_hook("scipy.sparse.csgraph._validation")
+ finder.recursion_depth_sparse = depth
+
+def hook_scipy_optimize(finder, module):
+ #import pdb;pdb.set_trace()
+ depth = getattr(finder,"recursion_depth_optimize",0)
+ if depth==0:
+ finder.recursion_depth_optimize = depth + 1
+ finder.import_hook("scipy.optimize.minpack2")
+ finder.recursion_depth_optimize = depth
Modified: trunk/py2exe-3/py2exe/mf3.py
===================================================================
--- trunk/py2exe-3/py2exe/mf3.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/mf3.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -17,12 +17,12 @@
import warnings
# XXX Clean up once str8's cstor matches bytes.
-LOAD_CONST = bytes([dis.opname.index('LOAD_CONST')])
-IMPORT_NAME = bytes([dis.opname.index('IMPORT_NAME')])
-STORE_NAME = bytes([dis.opname.index('STORE_NAME')])
-STORE_GLOBAL = bytes([dis.opname.index('STORE_GLOBAL')])
+LOAD_CONST = dis.opname.index('LOAD_CONST')
+IMPORT_NAME = dis.opname.index('IMPORT_NAME')
+STORE_NAME = dis.opname.index('STORE_NAME')
+STORE_GLOBAL = dis.opname.index('STORE_GLOBAL')
STORE_OPS = [STORE_NAME, STORE_GLOBAL]
-HAVE_ARGUMENT = bytes([dis.HAVE_ARGUMENT])
+HAVE_ARGUMENT = dis.HAVE_ARGUMENT
# Monkeypatch some missing methods in Python 3.3's NamespaceLoader
def __patch_py33():
@@ -317,11 +317,43 @@
try:
loader = importlib.find_loader(name, path)
except ValueError as details:
+ # XXX XXX XXX
+ # namespace modules only have these attributes (in Python 3.4, when
+ # a xxx.pth file is present in Lib/site-packages:
+ #
+ # __doc__: None
+ # __loader__: None
+ # __name__: <the module name>
+ # __package__: None
+ # __path__: [<the directory name>]
+ # __spec__: None
+ #
+ #
+ # When the xxx.pth file is NOT present:
+ #
+ # __doc__: None
+ # __loader__: <_frozen_importlib._NamespaceLoader object at ...>
+ # __name__: <the module name>
+ # __package__: <the module name>
+ # __path__: <_NamespacePath([<the directory name>]>
+ # __spec__: ModuleSpec(name=<module_name>, origin='namespace',
+ # submodule_search_locations=_NamespacePath([<dir name>]))
+
# Python 3.4 raises this error for namespace packages
if str(details) == "{}.__loader__ is None".format(name):
- msg = "Error: Namespace packages not yet supported: Skipping package {!r}"
- print(msg.format(name))
- loader = None
+ ## msg = "Error: Namespace packages not yet supported: Skipping package {!r}"
+ from importlib._bootstrap import _NamespaceLoader
+ ## print(msg.format(name))
+ ## loader = None
+ loader = _NamespaceLoader(name, path, None)
+ self._load_module(loader, name)
+ mod = self.modules[name]
+ real_mod = __import__(name)
+ print("PATH", path)
+ print("__path__", dir(real_mod))
+ mod.__path__ = real_mod.__path__
+ for n in dir(mod):
+ print(n, getattr(mod, n))
else:
raise
except AttributeError as details:
@@ -406,26 +438,43 @@
Scan the code object, and yield 'interesting' opcode combinations
"""
- code = co.co_code
- names = co.co_names
- consts = co.co_consts
- LOAD_LOAD_AND_IMPORT = LOAD_CONST + LOAD_CONST + IMPORT_NAME
- while code:
- c = bytes([code[0]])
- if c in STORE_OPS:
- oparg, = unpack('<H', code[1:3])
- yield "store", (names[oparg],)
- code = code[3:]
- continue
- if code[:9:3] == LOAD_LOAD_AND_IMPORT:
- oparg_1, oparg_2, oparg_3 = unpack('<xHxHxH', code[:9])
- yield "import", (consts[oparg_1], consts[oparg_2], names[oparg_3])
- code = code[9:]
- continue
- if c >= HAVE_ARGUMENT:
- code = code[3:]
- else:
- code = code[1:]
+ if hasattr(dis, "get_instructions"):
+ # dis.get_instructions() is only available in python 3.4
+ # and higher
+ instructions = []
+ for inst in dis.get_instructions(co):
+ instructions.append(inst)
+ c = inst.opcode
+ if c == IMPORT_NAME:
+ assert instructions[-3].opcode == LOAD_CONST
+ level = instructions[-3].argval
+ assert instructions[-2].opcode == LOAD_CONST
+ fromlist = instructions[-2].argval
+ name = inst.argval
+ yield "import", (level, fromlist, name)
+ elif c in STORE_OPS:
+ yield "store", (inst.argval,)
+ else:
+ code = co.co_code
+ names = co.co_names
+ consts = co.co_consts
+ LOAD_LOAD_AND_IMPORT = LOAD_CONST + LOAD_CONST + IMPORT_NAME
+ while code:
+ c = code[0]
+ if c in STORE_OPS:
+ oparg, = unpack('<H', code[1:3])
+ yield "store", (names[oparg],)
+ code = code[3:]
+ continue
+ if code[:9:3] == LOAD_LOAD_AND_IMPORT:
+ oparg_1, oparg_2, oparg_3 = unpack('<xHxHxH', code[:9])
+ yield "import", (consts[oparg_1], consts[oparg_2], names[oparg_3])
+ code = code[9:]
+ continue
+ if c >= HAVE_ARGUMENT:
+ code = code[3:]
+ else:
+ code = code[1:]
def ignore(self, name):
"""If the module or package with the given name is not found,
@@ -621,7 +670,11 @@
if self.__optimize__ == sys.flags.optimize:
self.__code_object__ = self.__loader__.get_code(self.__name__)
else:
- source = self.__source__
+ try:
+ source = self.__source__
+ except Exception:
+ import traceback; traceback.print_exc()
+ raise RuntimeError("loading %r" % self) from None
if source is not None:
# XXX??? for py3exe:
__file__ = self.__file__ \
Modified: trunk/py2exe-3/py2exe/mf34.py
===================================================================
--- trunk/py2exe-3/py2exe/mf34.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/mf34.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -1,4 +1,4 @@
-#!/usr/bin/python3.3
+#!/usr/bin/python3.4
# -*- coding: utf-8 -*-
"""ModuleFinder based on importlib
"""
@@ -14,6 +14,7 @@
import struct
import sys
import textwrap
+import warnings
# XXX Clean up once str8's cstor matches bytes.
LOAD_CONST = bytes([dis.opname.index('LOAD_CONST')])
@@ -23,31 +24,7 @@
STORE_OPS = [STORE_NAME, STORE_GLOBAL]
HAVE_ARGUMENT = bytes([dis.HAVE_ARGUMENT])
-# Monkeypatch some missing methods in Python 3.3's NamespaceLoader
-def __patch_py33():
- if sys.version_info < (3, 4):
- def is_package(self, fullname):
- return True
- def get_source(self, fullname):
- return ''
-
- def get_code(self, fullname):
- return compile('', '<string>', 'exec', dont_inherit=True)
-
- def init_module_attrs(self, module):
- module.__loader__ = self
- module.__package__ = module.__name__
- from importlib._bootstrap import NamespaceLoader
- NamespaceLoader.is_package = is_package
- NamespaceLoader.get_source = get_source
- NamespaceLoader.get_code = get_code
- NamespaceLoader.init_module_attrs = init_module_attrs
-
-__patch_py33()
-del __patch_py33
-
-
class ModuleFinder:
def __init__(self, path=None, verbose=0, excludes=None, optimize=0,
ignores=None):
@@ -79,7 +56,11 @@
"""
assert "__SCRIPT__" not in sys.modules
ldr = importlib.machinery.SourceFileLoader("__SCRIPT__", path)
- mod = Module(ldr, "__SCRIPT__", self._optimize)
+ if sys.version_info >= (3, 4):
+ spec = importlib.machinery.ModuleSpec("__SCRIPT__", ldr)
+ mod = Module(spec, "__SCRIPT__", self._optimize)
+ else:
+ mod = Module(ldr, "__SCRIPT__", self._optimize)
# Do NOT add it...
# self._add_module("__SCRIPT__", mod)
self._scan_code(mod.__code__, mod)
@@ -95,6 +76,8 @@
raise TypeError("{0} is not a package".format(name))
for finder, modname, ispkg in pkgutil.iter_modules(package.__path__):
self.safe_import_hook("%s.%s" % (name, modname))
+ if ispkg:
+ self.import_package("%s.%s" % (name, modname))
def import_hook(self, name, caller=None, fromlist=(), level=0):
@@ -298,14 +281,27 @@
msg = ('No module named {!r}; {} is not a package').format(name, parent)
self._add_badmodule(name)
raise ImportError(msg, name=name)
- loader = importlib.find_loader(name, path)
- if loader is None:
+ try:
+ spec = importlib.util.find_spec(name, path)
+ except ValueError as details:
+ # workaround for the .pth file for namespace packages that
+ # setuptools installs. The pth file inserts a 'damaged'
+ # module into sys.modules: it has no __spec__. Reloading
+ # the module helps (at least in Python3.4).
+ if details.args[0] == '{}.__spec__ is None'.format(name):
+ import imp
+ _ = __import__(name, path)
+ imp.reload(_)
+ spec = importlib.util.find_spec(name, path)
+ else:
+ raise
+ if spec is None:
self._add_badmodule(name)
raise ImportError(name)
elif name not in self.modules:
# The parent import may have already imported this module.
try:
- self._load_module(loader, name)
+ self._load_module(spec, name)
except ImportError:
self._add_badmodule(name)
raise
@@ -335,8 +331,8 @@
self.modules[name] = mod
- def _load_module(self, loader, name):
- mod = Module(loader, name, self._optimize)
+ def _load_module(self, spec, name):
+ mod = Module(spec, name, self._optimize)
self._add_module(name, mod)
if name in self._package_paths:
mod.__path__.extend(self._package_paths[name])
@@ -481,8 +477,10 @@
print("P", end=" ")
else:
print("m", end=" ")
- print("%-35s" % name, getattr(m, "__file__",
- "(built-in, frozen, or namespace)"))
+ if m.__spec__.has_location and hasattr(m, "__file__"):
+ print("%-35s" % name, getattr(m, "__file__"))
+ else:
+ print("%-35s" % name, "(%s)" % m.__spec__.origin)
deps = sorted(self._depgraph[name])
text = "\n".join(textwrap.wrap(", ".join(deps)))
print(" imported from:\n%s" % textwrap.indent(text, " "))
@@ -549,14 +547,16 @@
extension modules)
"""
- def __init__(self, loader, name, optimize):
+ def __init__(self, spec, name, optimize):
self.__optimize__ = optimize
self.__globalnames__ = set()
self.__name__ = name
- self.__loader__ = loader
+ self.__spec__ = spec
self.__code_object__ = None
+ loader = self.__loader__ = spec.loader
+
if hasattr(loader, "get_filename"):
# python modules
fnm = loader.get_filename(name)
@@ -569,6 +569,9 @@
self.__file__ = fnm
if loader.is_package(name):
self.__path__ = [os.path.dirname(fnm)]
+ elif spec.origin == "namespace":
+ # namespace modules have no loader
+ self.__path__ = spec.submodule_search_locations
else:
# frozen or builtin modules
if loader.is_package(name):
@@ -585,13 +588,12 @@
@property
def __code__(self):
- if self.__code_object__ is None:
+ if self.__code_object__ is None and self.__loader__ is not None:
if self.__optimize__ == sys.flags.optimize:
self.__code_object__ = self.__loader__.get_code(self.__name__)
else:
source = self.__source__
if source is not None:
- # XXX??? for py3exe:
__file__ = self.__file__ \
if hasattr(self, "__file__") else "<string>"
try:
Modified: trunk/py2exe-3/py2exe/py2exe_distutils.py
===================================================================
--- trunk/py2exe-3/py2exe/py2exe_distutils.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/py2exe_distutils.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -6,10 +6,12 @@
from distutils.command import build_ext, build
from distutils.sysconfig import customize_compiler
from distutils.dep_util import newer_group
-from distutils.errors import DistutilsError, DistutilsSetupError
+from distutils.errors import DistutilsError, DistutilsSetupError, DistutilsPlatformError
+from distutils.errors import CCompilerError, CompileError
from distutils.util import get_platform
+from distutils import log
-# We don't need a manifest in the executable, so monkeypath the code away:
+# We don't need a manifest in the executable, so monkeypatch the code away:
from distutils.msvc9compiler import MSVCCompiler
MSVCCompiler.manifest_setup_ldargs = lambda *args: None
@@ -40,134 +42,30 @@
description = "build special python interpreter stubs"
def finalize_options(self):
- build_ext.build_ext.finalize_options(self)
+ super().finalize_options()
self.interpreters = self.distribution.interpreters
- def run (self):
+ def run(self):
+ # Copied from build_ext.run() except that we use
+ # self.interpreters instead of self.extensions and
+ # self.build_interpreters() instead of self.build_extensions()
+ from distutils.ccompiler import new_compiler
+
if not self.interpreters:
return
- self.setup_compiler()
-
- # Now actually compile and link everything.
- for inter in self.interpreters:
- sources = inter.sources
- if sources is None or type(sources) not in (type([]), type(())):
- raise DistutilsSetupError(("in 'interpreters' option ('%s'), " +
- "'sources' must be present and must be " +
- "a list of source filenames") % inter.name)
- sources = list(sources)
-
- fullname = self.get_exe_fullname(inter.name)
- if self.inplace:
- # ignore build-lib -- put the compiled extension into
- # the source tree along with pure Python modules
- modpath = fullname.split('.')
- package = '.'.join(modpath[0:-1])
- base = modpath[-1]
-
- build_py = self.get_finalized_command('build_py')
- package_dir = build_py.get_package_dir(package)
- exe_filename = os.path.join(package_dir,
- self.get_exe_filename(base))
- else:
- exe_filename = os.path.join(self.build_lib,
- self.get_exe_filename(fullname))
- if inter.target_desc == "executable":
- exe_filename += ".exe"
- else:
- exe_filename += ".dll"
-
- if not (self.force or \
- newer_group(sources + inter.depends, exe_filename, 'newer')):
- self.announce("skipping '%s' interpreter (up-to-date)" %
- inter.name)
- continue # 'for' loop over all interpreters
- else:
- self.announce("building '%s' interpreter" % inter.name)
-
- extra_args = inter.extra_compile_args or []
-
- macros = inter.define_macros[:]
- for undef in inter.undef_macros:
- macros.append((undef,))
-
- objects = self.compiler.compile(sources,
- output_dir=self.build_temp,
- macros=macros,
- include_dirs=inter.include_dirs,
- debug=self.debug,
- extra_postargs=extra_args,
- depends=inter.depends)
-
- if inter.extra_objects:
- objects.extend(inter.extra_objects)
- extra_args = inter.extra_link_args or []
-
- if inter.export_symbols:
- # The mingw32 compiler writes a .def file containing
- # the export_symbols. Since py2exe uses symbols in
- # the extended form 'DllCanUnloadNow,PRIVATE' (to
- # avoid MS linker warnings), we have to replace the
- # comma(s) with blanks, so that the .def file can be
- # properly parsed.
- # XXX MingW32CCompiler, or CygwinCCompiler ?
- from distutils.cygwinccompiler import Mingw32CCompiler
- if isinstance(self.compiler, Mingw32CCompiler):
- inter.export_symbols = [s.replace(",", " ") for s in inter.export_symbols]
- inter.export_symbols = [s.replace("=", "\t") for s in inter.export_symbols]
-
- # XXX - is msvccompiler.link broken? From what I can see, the
- # following should work, instead of us checking the param:
- self.compiler.link(inter.target_desc,
- objects, exe_filename,
- libraries=self.get_libraries(inter),
- library_dirs=inter.library_dirs,
- runtime_library_dirs=inter.runtime_library_dirs,
- export_symbols=inter.export_symbols,
- extra_postargs=extra_args,
- debug=self.debug)
- # build_extensions ()
-
- def get_exe_fullname (self, inter_name):
- if self.package is None:
- return inter_name
- else:
- return self.package + '.' + inter_name
-
- def get_exe_filename (self, inter_name):
- ext_path = inter_name.split('.')
- if self.debug:
- fnm = os.path.join(*ext_path) + '_d'
- else:
- fnm = os.path.join(*ext_path)
- if ext_path[-1] == "resources":
- return fnm
- return '%s-py%s.%s-%s' % (fnm, sys.version_info[0], sys.version_info[1], get_platform())
-
- def setup_compiler(self):
- # This method *should* be available separately in build_ext!
- from distutils.ccompiler import new_compiler
-
- # If we were asked to build any C/C++ libraries, make sure that the
- # directory where we put them is in the library search path for
- # linking interpreters.
- if self.distribution.has_c_libraries():
- build_clib = self.get_finalized_command('build_clib')
- self.libraries.extend(build_clib.get_library_names() or [])
- self.library_dirs.append(build_clib.build_clib)
-
# Setup the CCompiler object that we'll use to do all the
# compiling and linking
self.compiler = new_compiler(compiler=self.compiler,
verbose=self.verbose,
dry_run=self.dry_run,
force=self.force)
- try:
- self.compiler.initialize()
- except AttributeError:
- pass # initialize doesn't exist before 2.5
customize_compiler(self.compiler)
+ # If we are cross-compiling, init the compiler now (if we are not
+ # cross-compiling, init would not hurt, but people may rely on
+ # late initialization of compiler even if they shouldn't...)
+ if os.name == 'nt' and self.plat_name != get_platform():
+ self.compiler.initialize(self.plat_name)
# And make sure that any compile/link-related options (which might
# come from the command-line or from the setup script) are set in
@@ -176,8 +74,8 @@
if self.include_dirs is not None:
self.compiler.set_include_dirs(self.include_dirs)
if self.define is not None:
- # 'define' option is a list of (name, value) tuples
- for (name,value) in self.define:
+ # 'define' option is a list of (name,value) tuples
+ for (name, value) in self.define:
self.compiler.define_macro(name, value)
if self.undef is not None:
for macro in self.undef:
@@ -191,10 +89,125 @@
if self.link_objects is not None:
self.compiler.set_link_objects(self.link_objects)
- # setup_compiler()
+ # Now actually compile and link everything.
+ self.build_interpreters()
-# class BuildInterpreters
+ def build_interpreters(self):
+ for interp in self.interpreters:
+ self.build_interp(interp)
+
+ def build_interp(self, ext):
+ sources = ext.sources
+ if sources is None or not isinstance(sources, (list, tuple)):
+ raise DistutilsSetupError(
+ "in 'interpreters' option (extension '%s'), "
+ "'sources' must be present and must be "
+ "a list of source filenames" % ext.name)
+ sources = list(sources)
+
+ ext_path = self.get_ext_fullpath(ext.name)
+
+ if ext.target_desc == "executable":
+ ext_path += ".exe"
+ else:
+ ext_path += ".dll"
+
+ depends = sources + ext.depends
+ if not (self.force or newer_group(depends, ext_path, 'newer')):
+ log.debug("skipping '%s' extension (up-to-date)", ext.name)
+ return
+ else:
+ log.info("building '%s' extension", ext.name)
+
+ # First, compile the source code to object files.
+
+ # XXX not honouring 'define_macros' or 'undef_macros' -- the
+ # CCompiler API needs to change to accommodate this, and I
+ # want to do one thing at a time!
+
+ # Two possible sources for extra compiler arguments:
+ # - 'extra_compile_args' in Extension object
+ # - CFLAGS environment variable (not particularly
+ # elegant, but people seem to expect it and I
+ # guess it's useful)
+ # The environment variable should take precedence, and
+ # any sensible compiler will give precedence to later
+ # command line args. Hence we combine them in order:
+ extra_args = ext.extra_compile_args or []
+
+ macros = ext.define_macros[:]
+ for undef in ext.undef_macros:
+ macros.append((undef,))
+
+ objects = self.compiler.compile(sources,
+ output_dir=self.build_temp,
+ macros=macros,
+ include_dirs=ext.include_dirs,
+ debug=self.debug,
+ extra_postargs=extra_args,
+ depends=ext.depends)
+
+ # XXX -- this is a Vile HACK!
+ #
+ # The setup.py script for Python on Unix needs to be able to
+ # get this list so it can perform all the clean up needed to
+ # avoid keeping object files around when cleaning out a failed
+ # build of an extension module. Since Distutils does not
+ # track dependencies, we have to get rid of intermediates to
+ # ensure all the intermediates will be properly re-built.
+ #
+ self._built_objects = objects[:]
+
+ # Now link the object files together into a "shared object" --
+ # of course, first we have to figure out all the other things
+ # that go into the mix.
+ if ext.extra_objects:
+ objects.extend(ext.extra_objects)
+ extra_args = ext.extra_link_args or []
+
+ # Detect target language, if not provided
+## language = ext.language or self.compiler.detect_language(sources)
+
+ ## self.compiler.link_shared_object(
+ ## objects, ext_path,
+ ## libraries=self.get_libraries(ext),
+ ## library_dirs=ext.library_dirs,
+ ## runtime_library_dirs=ext.runtime_library_dirs,
+ ## extra_postargs=extra_args,
+ ## export_symbols=self.get_export_symbols(ext),
+ ## debug=self.debug,
+ ## build_temp=self.build_temp,
+ ## target_lang=language)
+
+ # Hm, for Python 3.5 to link a shared library (instead of exe
+ # or pyd) we need to add /DLL to the linker arguments.
+ # Currently this is done in the setup script; should we do it
+ # here?
+
+ self.compiler.link(ext.target_desc,
+ objects, ext_path,
+ libraries=self.get_libraries(ext),
+ library_dirs=ext.library_dirs,
+ runtime_library_dirs=ext.runtime_library_dirs,
+ export_symbols=ext.export_symbols,
+ extra_postargs=extra_args,
+ debug=self.debug)
+
+
+ # -- Name generators -----------------------------------------------
+
+ def get_ext_filename (self, inter_name):
+ ext_path = inter_name.split('.')
+ if self.debug:
+ fnm = os.path.join(*ext_path) + '_d'
+ else:
+ fnm = os.path.join(*ext_path)
+ if ext_path[-1] == "resources":
+ return fnm
+ return '%s-py%s.%s-%s' % (fnm, sys.version_info[0], sys.version_info[1], get_platform())
+
+
def InstallSubCommands():
"""Adds our own sub-commands to build and install"""
has_interpreters = lambda self: self.distribution.has_interpreters()
Modified: trunk/py2exe-3/py2exe/runtime.py
===================================================================
--- trunk/py2exe-3/py2exe/runtime.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/py2exe/runtime.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -423,7 +423,7 @@
arc.writestr(path, stream.getvalue())
elif hasattr(mod, "__file__"):
- assert mod.__file__.endswith(EXTENSION_SUFFIXES[0])
+ assert mod.__file__.endswith(tuple(EXTENSION_SUFFIXES))
if self.options.bundle_files <= 2:
# put .pyds into the archive
arcfnm = mod.__name__.replace(".", "\\") + EXTENSION_SUFFIXES[0]
@@ -495,7 +495,7 @@
# nothing to do for python modules.
continue
if hasattr(mod, "__file__"):
- assert mod.__file__.endswith(EXTENSION_SUFFIXES[0])
+ assert mod.__file__.endswith(tuple(EXTENSION_SUFFIXES))
pydfile = mod.__name__ + EXTENSION_SUFFIXES[0]
dst = os.path.join(libdir, pydfile)
Modified: trunk/py2exe-3/setup.py
===================================================================
--- trunk/py2exe-3/setup.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/setup.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -40,11 +40,12 @@
extra_link_args = []
if 0:
- # enable this to debug a release build
+ # XXX enable this to debug a release build, otherwise let disabled
+ # because the .PDB files are huge.
extra_compile_args.append("/Od")
extra_compile_args.append("/Z7")
extra_link_args.append("/DEBUG")
- macros.append(("VERBOSE", "1"))
+ #macros.append(("VERBOSE", "1"))
run_ctypes_dll = Interpreter("py2exe.run_ctypes_dll",
["source/run_ctypes_dll.c",
@@ -67,7 +68,7 @@
target_desc = "shared_library",
define_macros=macros,
extra_compile_args=extra_compile_args,
- extra_link_args=extra_link_args,
+ extra_link_args=extra_link_args + ["/DLL"],
)
run = Interpreter("py2exe.run",
@@ -119,7 +120,7 @@
["source/dll.c",
"source/icon.rc"],
target_desc = "shared_library",
- extra_link_args=["/NOENTRY"],
+ extra_link_args=["/DLL", "/NOENTRY"],
)
interpreters = [run, run_w, resource_dll,
@@ -132,12 +133,12 @@
else:
class my_bdist_wheel(bdist_wheel.bdist_wheel):
"""We change the bdist_wheel command so that it creates a
- wheel-file compatible with Python 3.3 and Python 3.4 only by
- setting the impl_tag to py33.py34.
+ wheel-file compatible with CPython, 3.4, 3.5, and 3.6 only
+ by setting the impl_tag to 'cp33.cp34.cp35.cp36'
"""
def get_tag(self):
impl_tag, abi_tag, plat_tag = super().get_tag()
- return "py33.py34", abi_tag, plat_tag
+ return "cp33.cp34.cp35.cp36", abi_tag, plat_tag
if __name__ == "__main__":
Modified: trunk/py2exe-3/source/MyLoadLibrary.c
===================================================================
--- trunk/py2exe-3/source/MyLoadLibrary.c 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/source/MyLoadLibrary.c 2017-01-04 15:34:08 UTC (rev 766)
@@ -198,7 +198,8 @@
if (lib)
return lib->module;
SetLastError(0);
- return GetModuleHandle(name);
+ return NULL;
+ //return GetModuleHandle(name);
}
HMODULE MyLoadLibrary(LPCSTR name, void *bytes, void *userdata)
Modified: trunk/py2exe-3/source/Python-dynload.h
===================================================================
--- trunk/py2exe-3/source/Python-dynload.h 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/source/Python-dynload.h 2017-01-04 15:34:08 UTC (rev 766)
@@ -1,9 +1,11 @@
#define Py_OptimizeFlag *(_Py_OptimizeFlag_PTR())
#define Py_NoSiteFlag *(_Py_NoSiteFlag_PTR())
#define Py_VerboseFlag *(_Py_VerboseFlag_PTR())
+#define _Py_PackageContext *(__Py_PackageContext_PTR())
extern int *_Py_OptimizeFlag_PTR();
extern int *_Py_NoSiteFlag_PTR();
extern int *_Py_VerboseFlag_PTR();
+extern char **__Py_PackageContext_PTR();
extern int PythonLoaded(HMODULE hmod);
Modified: trunk/py2exe-3/source/_memimporter.c
===================================================================
--- trunk/py2exe-3/source/_memimporter.c 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/source/_memimporter.c 2017-01-04 15:34:08 UTC (rev 766)
@@ -52,7 +52,7 @@
PyObject* (*p)(void);
PyObject *m = NULL;
struct PyModuleDef *def;
-// char *oldcontext;
+ char *oldcontext;
PyObject *name = PyUnicode_FromString(modname);
if (name == NULL)
@@ -75,16 +75,16 @@
Py_DECREF(name);
return -1;
}
-/*
+
oldcontext = _Py_PackageContext;
_Py_PackageContext = modname;
-*/
+
p = (PyObject*(*)(void))init_func;
m = (*p)();
-/*
+
_Py_PackageContext = oldcontext;
-*/
+
if (PyErr_Occurred()) {
Py_DECREF(name);
return -1;
Modified: trunk/py2exe-3/source/python-dynload.c
===================================================================
--- trunk/py2exe-3/source/python-dynload.c 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/source/python-dynload.c 2017-01-04 15:34:08 UTC (rev 766)
@@ -55,6 +55,11 @@
DATA(int *, Py_VerboseFlag);
}
+char **__Py_PackageContext_PTR()
+{
+ DATA(char **, _Py_PackageContext);
+}
+
////////////////////////////////////////////////////////////////
int Py_IsInitialized(void)
Modified: trunk/py2exe-3/source/run_ctypes_dll.c
===================================================================
--- trunk/py2exe-3/source/run_ctypes_dll.c 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/source/run_ctypes_dll.c 2017-01-04 15:34:08 UTC (rev 766)
@@ -81,6 +81,7 @@
extern int init_with_instance(HMODULE, char *);
extern void fini();
extern int run_script(void);
+extern wchar_t libfilename[_MAX_PATH + _MAX_FNAME + _MAX_EXT];
#include "MyLoadLibrary.h"
@@ -90,7 +91,9 @@
int load_ctypes(void)
{
char dll_path[_MAX_PATH+_MAX_FNAME+1];
-
+ wchar_t ctypes_path[_MAX_PATH+_MAX_FNAME+1];
+ wchar_t * temp=NULL;
+ int length=0;
// shouldn't do this twice
assert(g_ctypes == NULL);
@@ -104,7 +107,14 @@
if (g_ctypes == NULL) {
// not already loaded - try and load from the current dir
// char *temp;
- GetModuleFileNameA(gInstance, dll_path, sizeof(dll_path));
+ //wrong, this is myself, makes an endless loop...
+ //GetModuleFileNameA(gInstance, dll_path, sizeof(dll_path));
+ temp=wcsrchr(libfilename,L'\\');
+ length=temp-(wchar_t*)libfilename+1;
+ wcscpy(ctypes_path,libfilename);
+ ctypes_path[length]=L'\0';
+ wcscat(ctypes_path,L"_ctypes.pyd");
+
/* ???
temp = dll_path + strlen(dll_path);
while (temp>dll_path && *temp != '\\')
@@ -113,13 +123,14 @@
// temp points to '\\filename.ext'!
*/
/* ???
+
#ifdef _DEBUG
g_ctypes = MyGetModuleHandle("_ctypes_d.pyd");
#else
g_ctypes = MyGetModuleHandle("_ctypes.pyd");
#endif
*/
- g_ctypes = LoadLibraryEx(dll_path, // points to name of executable module
+ g_ctypes = LoadLibraryExW(ctypes_path, // points to name of executable module
NULL, // HANDLE hFile, // reserved, must be NULL
LOAD_WITH_ALTERED_SEARCH_PATH // DWORD dwFlags // entry-point execution flag
);
@@ -202,7 +213,8 @@
// *****************************************************************
BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
{
- if ( dwReason == DLL_PROCESS_ATTACH) {
+ OutputDebugString("DllMain");
+ if ( dwReason == DLL_PROCESS_ATTACH) {
gInstance = hInstance;
InitializeCriticalSection(&csInit);
_MyLoadActCtxPointers();
@@ -224,7 +236,10 @@
HRESULT __stdcall DllCanUnloadNow(void)
{
HRESULT rc;
+ ULONG_PTR cookie = 0;
+ cookie = _My_ActivateActCtx(); // some windows manifest magic...
check_init();
+ _My_DeactivateActCtx(cookie);
assert(Pyc_DllCanUnloadNow);
if (!Pyc_DllCanUnloadNow) return E_UNEXPECTED;
rc = Pyc_DllCanUnloadNow();
@@ -235,10 +250,22 @@
HRESULT __stdcall DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppv)
{
HRESULT rc;
+ ULONG_PTR cookie = 0;
+ /*
+ OutputDebugString("DllGetClassObject");
+
+ MessageBox(NULL,"Debug\n",
+ "DllGetClassObject",
+ MB_OK | MB_ICONINFORMATION);
+ */
+ cookie = _My_ActivateActCtx(); // some windows manifest magic...
check_init();
+
assert(Pyc_DllGetClassObject);
if (!Pyc_DllGetClassObject) return E_UNEXPECTED;
rc = Pyc_DllGetClassObject(rclsid, riid, ppv);
+ _My_DeactivateActCtx(cookie);
+
return rc;
}
@@ -247,8 +274,28 @@
{
int rc=0;
PyGILState_STATE state;
+ wchar_t buf[300];
+ ULONG_PTR cookie = 0;
+
+ OutputDebugString("DllRegisterServer");
+ /*
+ MessageBox(NULL,
+ "Debug\n",
+ "DllregisterServer",
+ MB_OK | MB_ICONINFORMATION);
+ */
+ cookie = _My_ActivateActCtx(); // some windows manifest magic...
check_init();
+ _My_DeactivateActCtx(cookie);
+
+ OutputDebugString("check_init ok");
+
state = PyGILState_Ensure();
+ OutputDebugString("PyGILState_Ensure done");
+
+ swprintf(buf,300,L"DllRegisterServer: libfilename=%s\n",&libfilename);
+ OutputDebugStringW(buf);
+
rc = PyRun_SimpleString("DllRegisterServer()\n");
if (rc != 0)
PyErr_Print();
@@ -260,7 +307,11 @@
{
int rc=0;
PyGILState_STATE state;
+ ULONG_PTR cookie = 0;
+ cookie = _My_ActivateActCtx(); // some windows manifest magic...
check_init();
+ _My_DeactivateActCtx(cookie);
+
state = PyGILState_Ensure();
rc = PyRun_SimpleString("DllUnregisterServer()\n");
if (rc != 0)
Modified: trunk/py2exe-3/zipextimporter.py
===================================================================
--- trunk/py2exe-3/zipextimporter.py 2014-10-21 15:22:50 UTC (rev 765)
+++ trunk/py2exe-3/zipextimporter.py 2017-01-04 15:34:08 UTC (rev 766)
@@ -75,6 +75,7 @@
def load_module(self, fullname):
verbose = _memimporter.get_verbose_flag()
+
if fullname in sys.modules:
mod = sys.modules[fullname]
if verbose:
@@ -84,37 +85,39 @@
return mod
try:
return zipimport.zipimporter.load_module(self, fullname)
- except ImportError:
- pass
- if sys.version_info >= (3, 0):
- # name of initfunction
- initname = "PyInit_" + fullname.split(".")[-1]
- else:
- # name of initfunction
- initname = "init" + fullname.split(".")[-1]
- filename = fullname.replace(".", "\\")
- if filename in ("pywintypes", "pythoncom"):
- filename = filename + "%d%d" % sys.version_info[:2]
- suffixes = ('.dll',)
- else:
- suffixes = self._suffixes
- for s in suffixes:
- path = filename + s
- if path in self._files:
- if verbose > 1:
- sys.stderr.write("# found %s in zipfile %s\n"
- % (path, self.archive))
- mod = _memimporter.import_module(fullname, path,
- initname,
- self.get_data)
- mod.__file__ = "%s\\%s" % (self.archive, path)
- mod.__loader__ = self
- if verbose:
- sys.stderr.write("import %s # loaded from zipfile %s\n"
- % (fullname, mod.__file__))
- return mod
- raise zipimport.ZipImportError("can't find module %s" % fullname)
+ except ImportError as err:
+ if verbose:
+ sys.stderr.write("error loading %s: %s\n"% (fullname, err))
+ if sys.version_info >= (3, 0):
+ # name of initfunction
+ initname = "PyInit_" + fullname.split(".")[-1]
+ else:
+ # name of initfunction
+ initname = "init" + fullname.split(".")[-1]
+ filename = fullname.replace(".", "\\")
+ if filename in ("pywintypes", "pythoncom"):
+ filename = filename + "%d%d" % sys.version_info[:2]
+ suffixes = ('.dll',)
+ else:
+ suffixes = self._suffixes
+ for s in suffixes:
+ path = filename + s
+ if path in self._files:
+ if verbose > 1:
+ sys.stderr.write("# found %s in zipfile %s\n"
+ % (path, self.archive))
+ mod = _memimporter.import_module(fullname, path,
+ initname,
+ self.get_data)
+ mod.__file__ = "%s\\%s" % (self.archive, path)
+ mod.__loader__ = self
+ if verbose:
+ sys.stderr.write("import %s # loaded from zipfile %s\n"
+ % (fullname, mod.__file__))
+ return mod
+ raise zipimport.ZipImportError("can't find module %s" % fullname) from err
+
def __repr__(self):
return "<%s object %r>" % (self.__class__.__name__, self.archive)
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|