aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJon Turney <jon.turney@dronecode.org.uk>2018-01-14 21:10:51 +0000
committerJon Turney <jon.turney@dronecode.org.uk>2018-01-15 20:27:48 +0000
commit153a7fb33240dc04f459147b418f58e30d448d56 (patch)
treec6630331583be489fb47e9aa4815564b57f2328b
parent8efdcca93063fb224c53ae2d6f57b8dacf082456 (diff)
downloadmeson-153a7fb33240dc04f459147b418f58e30d448d56.zip
meson-153a7fb33240dc04f459147b418f58e30d448d56.tar.gz
meson-153a7fb33240dc04f459147b418f58e30d448d56.tar.bz2
Fix unpickling of dynamic subclasses of ConfigToolDependency
This code isn't used as present: the actual objects we use and which get pickled are either static subclasses of ConfigToolDependency, or special purpos subclasses of Dependency which get attributes copied from an instance of a dynamic subclass of ConfigToolDependency which is then discarded. This is fortunate, as it doesn't work: the pickled reduction is a call to the dynamic subclass's constructor, but the superclass constructors rely on the environment object being fully initialized, which hasn't happened yet during unpickling. Avoid this by having a pickled reduction which is just a call to create the dynamic subclass object, and relying on the default __setstate__ behavior to unpickle the object's __dict__.
-rw-r--r--mesonbuild/dependencies/base.py9
1 files changed, 6 insertions, 3 deletions
diff --git a/mesonbuild/dependencies/base.py b/mesonbuild/dependencies/base.py
index fa50761..20a234d 100644
--- a/mesonbuild/dependencies/base.py
+++ b/mesonbuild/dependencies/base.py
@@ -236,14 +236,17 @@ class ConfigToolDependency(ExternalDependency):
# instantiated and returned. The reduce function (method) is also
# attached, since python's pickle module won't be able to do anything
# with this dynamically generated class otherwise.
- def reduce(_):
- return (cls.factory,
- (name, environment, language, kwargs, tools, tool_name))
+ def reduce(self):
+ return (cls._unpickle, (), self.__dict__)
sub = type('{}Dependency'.format(name.capitalize()), (cls, ),
{'tools': tools, 'tool_name': tool_name, '__reduce__': reduce})
return sub(name, environment, language, kwargs)
+ @classmethod
+ def _unpickle(cls):
+ return cls.__new__(cls)
+
def find_config(self, versions=None):
"""Helper method that searchs for config tool binaries in PATH and
returns the one that best matches the given version requirements.