diff options
author | Jörg Frings-Fürst <debian@jff-webhosting.net> | 2017-10-03 06:26:58 +0200 |
---|---|---|
committer | Jörg Frings-Fürst <debian@jff-webhosting.net> | 2017-10-03 06:26:58 +0200 |
commit | 27b47b5db42407baf5d704bf52c35015b2c0ad7b (patch) | |
tree | 320f8d5fc315c211f7d073891bd7117754f5f5b3 /src/engine/SCons/compat/__init__.py | |
parent | 6be31f5d140b81227911cabfc61d3802c76c1b61 (diff) | |
parent | fabd454ddf505302bf41ef4da0609437c29d5605 (diff) |
Merge branch 'release/3.0.0+repack-1'3.0.0+repack-1
Diffstat (limited to 'src/engine/SCons/compat/__init__.py')
-rw-r--r-- | src/engine/SCons/compat/__init__.py | 92 |
1 files changed, 82 insertions, 10 deletions
diff --git a/src/engine/SCons/compat/__init__.py b/src/engine/SCons/compat/__init__.py index d3d4fe6..7973732 100644 --- a/src/engine/SCons/compat/__init__.py +++ b/src/engine/SCons/compat/__init__.py @@ -1,5 +1,5 @@ # -# Copyright (c) 2001 - 2016 The SCons Foundation +# Copyright (c) 2001 - 2017 The SCons Foundation # # Permission is hereby granted, free of charge, to any person obtaining # a copy of this software and associated documentation files (the @@ -57,11 +57,14 @@ function defined below loads the module as the "real" name (without the rest of our code will find our pre-loaded compatibility module. """ -__revision__ = "src/engine/SCons/compat/__init__.py rel_2.5.1:3735:9dc6cee5c168 2016/11/03 14:02:02 bdbaddog" +__revision__ = "src/engine/SCons/compat/__init__.py rel_3.0.0:4395:8972f6a2f699 2017/09/18 12:59:24 bdbaddog" import os import sys -import imp # Use the "imp" module to protect imports from fixers. +import imp # Use the "imp" module to protect imports from fixers. + +PYPY = hasattr(sys, 'pypy_translation_info') + def import_as(module, name): """ @@ -71,6 +74,7 @@ def import_as(module, name): dir = os.path.split(__file__)[0] return imp.load_module(name, *imp.find_module(module, [dir])) + def rename_module(new, old): """ Attempts to import the old module and load it under the new name. @@ -82,21 +86,32 @@ def rename_module(new, old): except ImportError: return False + +# TODO: FIXME # In 3.x, 'pickle' automatically loads the fast version if available. rename_module('pickle', 'cPickle') +# Default pickle protocol. Higher protocols are more efficient/featureful +# but incompatible with older Python versions. On Python 2.7 this is 2. +# Negative numbers choose the highest available protocol. +import pickle + +# Was pickle.HIGHEST_PROTOCOL +# Changed to 2 so py3.5+'s pickle will be compatible with py2.7. +PICKLE_PROTOCOL = 2 + +# TODO: FIXME # In 3.x, 'profile' automatically loads the fast version if available. rename_module('profile', 'cProfile') - +# TODO: FIXME # Before Python 3.0, the 'queue' module was named 'Queue'. rename_module('queue', 'Queue') - +# TODO: FIXME # Before Python 3.0, the 'winreg' module was named '_winreg' rename_module('winreg', '_winreg') - # Python 3 moved builtin intern() to sys package # To make porting easier, make intern always live # in sys package (for python 2.7.x) @@ -107,32 +122,89 @@ except AttributeError: # intern into the sys package sys.intern = intern - # Preparing for 3.x. UserDict, UserList, UserString are in # collections for 3.x, but standalone in 2.7.x import collections + try: collections.UserDict except AttributeError: - exec('from UserDict import UserDict as _UserDict') + exec ('from UserDict import UserDict as _UserDict') collections.UserDict = _UserDict del _UserDict try: collections.UserList except AttributeError: - exec('from UserList import UserList as _UserList') + exec ('from UserList import UserList as _UserList') collections.UserList = _UserList del _UserList try: collections.UserString except AttributeError: - exec('from UserString import UserString as _UserString') + exec ('from UserString import UserString as _UserString') collections.UserString = _UserString del _UserString +import shutil +try: + shutil.SameFileError +except AttributeError: + class SameFileError(Exception): + pass + + shutil.SameFileError = SameFileError + +def with_metaclass(meta, *bases): + """ + Function from jinja2/_compat.py. License: BSD. + + Use it like this:: + + class BaseForm(object): + pass + + class FormType(type): + pass + + class Form(with_metaclass(FormType, BaseForm)): + pass + + This requires a bit of explanation: the basic idea is to make a + dummy metaclass for one level of class instantiation that replaces + itself with the actual metaclass. Because of internal type checks + we also need to make sure that we downgrade the custom metaclass + for one level to something closer to type (that's why __call__ and + __init__ comes back from type etc.). + + This has the advantage over six.with_metaclass of not introducing + dummy classes into the final MRO. + """ + + class metaclass(meta): + __call__ = type.__call__ + __init__ = type.__init__ + + def __new__(cls, name, this_bases, d): + if this_bases is None: + return type.__new__(cls, name, (), d) + return meta(name, bases, d) + + return metaclass('temporary_class', None, {}) + + +class NoSlotsPyPy(type): + """ + Workaround for PyPy not working well with __slots__ and __class__ assignment. + """ + + def __new__(meta, name, bases, dct): + if PYPY and '__slots__' in dct: + dct.pop('__slots__') + return super(NoSlotsPyPy, meta).__new__(meta, name, bases, dct) + # Local Variables: # tab-width:4 # indent-tabs-mode:nil |