Bug 1316844 - Improve function unwrapping to properly cover templates. r=chmanchester

--HG--
extra : rebase_source : 35b56b6a2507bf18ef8182c3d8852bad5d13075f
This commit is contained in:
Mike Hommey 2016-11-11 11:32:43 +09:00
parent aced3b2ee7
commit 1844bdb554
2 changed files with 23 additions and 10 deletions

View File

@ -660,7 +660,7 @@ class ConfigureSandbox(dict):
# file. It can however depend on variables from the closure, thus
# maybe_prepare_function and isfunction are declared above to be
# available there.
@wraps(template)
@self.wraps(template)
def wrapper(*args, **kwargs):
args = [maybe_prepare_function(arg) for arg in args]
kwargs = {k: maybe_prepare_function(v)
@ -674,7 +674,7 @@ class ConfigureSandbox(dict):
# decorator, so mark the returned function as wrapping the
# function passed in.
if len(args) == 1 and not kwargs and isfunction(args[0]):
ret = wraps(args[0])(ret)
ret = self.wraps(args[0])(ret)
return wrap_template(ret)
return ret
return wrapper
@ -683,6 +683,9 @@ class ConfigureSandbox(dict):
self._templates.add(wrapper)
return wrapper
def wraps(self, func):
return wraps(func)
RE_MODULE = re.compile('^[a-zA-Z0-9_\.]+$')
def imports_impl(self, _import, _from=None, _as=None):
@ -917,14 +920,14 @@ class ConfigureSandbox(dict):
closure = tuple(makecell(cell.cell_contents)
for cell in func.func_closure)
new_func = wraps(func)(types.FunctionType(
new_func = self.wraps(func)(types.FunctionType(
func.func_code,
glob,
func.__name__,
func.func_defaults,
closure
))
@wraps(new_func)
@self.wraps(new_func)
def wrapped(*args, **kwargs):
if func in self._imports:
self._apply_imports(func, glob)

View File

@ -4,12 +4,14 @@
from __future__ import absolute_import, print_function, unicode_literals
from functools import wraps
from StringIO import StringIO
from . import (
CombinedDependsFunction,
ConfigureError,
ConfigureSandbox,
DependsFunction,
SandboxedGlobal,
)
from .lint_util import disassemble_as_iter
from mozbuild.util import memoize
@ -37,7 +39,7 @@ class LintSandbox(ConfigureSandbox):
if (self._help_option in obj.dependencies or
obj in (self._always, self._never)):
return False
func, glob = self._wrapped[obj.func]
func, glob = self.unwrap(obj.func)
# We allow missing --help dependencies for functions that:
# - don't use @imports
# - don't have a closure
@ -71,8 +73,16 @@ class LintSandbox(ConfigureSandbox):
return super(LintSandbox, self)._value_for_depends(
obj, need_help_dependency)
def _prepare_function(self, func):
wrapped, glob = super(LintSandbox, self)._prepare_function(func)
if wrapped not in self._wrapped:
self._wrapped[wrapped] = func, glob
return wrapped, glob
def unwrap(self, func):
glob = func.func_globals
while func in self._wrapped:
if isinstance(func.func_globals, SandboxedGlobal):
glob = func.func_globals
func = self._wrapped[func]
return func, glob
def wraps(self, func):
def do_wraps(wrapper):
self._wrapped[wrapper] = func
return wraps(func)(wrapper)
return do_wraps