chore: import upstream snapshot with attribution
This commit is contained in:
@@ -0,0 +1,314 @@
|
||||
# Copyright (c) 2020 PaddlePaddle Authors. All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import inspect
|
||||
import unittest
|
||||
|
||||
import numpy as np
|
||||
from dygraph_to_static_utils import (
|
||||
Dy2StTestBase,
|
||||
)
|
||||
from numpy import append
|
||||
|
||||
import paddle
|
||||
from paddle.jit.dy2static.transformers.utils import FunctionNameLivenessAnalysis
|
||||
from paddle.utils import gast
|
||||
|
||||
global_a = []
|
||||
|
||||
|
||||
class JudgeVisitor(gast.NodeVisitor):
|
||||
def __init__(self, ans, mod):
|
||||
self.ans = ans
|
||||
self.mod = mod
|
||||
|
||||
def visit_FunctionDef(self, node):
|
||||
scope = node.pd_scope
|
||||
expected = self.ans.get(node.name, set())
|
||||
exp_mod = self.mod.get(node.name, set())
|
||||
assert scope.existed_vars() == expected, "Not Equals."
|
||||
assert scope.modified_vars() == exp_mod, (
|
||||
f"Not Equals in function:{node.name} . expect {exp_mod} , but get {scope.modified_vars()}"
|
||||
)
|
||||
self.generic_visit(node)
|
||||
|
||||
|
||||
class JudgePushPopVisitor(gast.NodeVisitor):
|
||||
def __init__(self, push_pop_vars):
|
||||
self.pp_var = push_pop_vars
|
||||
|
||||
def visit_FunctionDef(self, node):
|
||||
scope = node.pd_scope
|
||||
expected = self.pp_var.get(node.name, set())
|
||||
assert scope.push_pop_vars == expected, (
|
||||
f"Not Equals in function:{node.name} . expect {expected} , but get {scope.push_pop_vars}"
|
||||
)
|
||||
self.generic_visit(node)
|
||||
|
||||
|
||||
def test_normal_0(x):
|
||||
def func():
|
||||
if True:
|
||||
i = 1
|
||||
|
||||
func()
|
||||
return i
|
||||
|
||||
|
||||
def test_normal_argument(x):
|
||||
x = 1
|
||||
|
||||
def func():
|
||||
if True:
|
||||
print(x)
|
||||
i = 1
|
||||
|
||||
func()
|
||||
return x
|
||||
|
||||
|
||||
def test_global(x):
|
||||
global t
|
||||
t = 10
|
||||
|
||||
def func():
|
||||
if True:
|
||||
print(x)
|
||||
i = 1
|
||||
|
||||
func()
|
||||
return x
|
||||
|
||||
|
||||
def test_nonlocal(x, *args, **kargs):
|
||||
i = 10
|
||||
|
||||
def func(*args, **kargs):
|
||||
nonlocal i
|
||||
k = 10
|
||||
if True:
|
||||
print(x)
|
||||
i = 1
|
||||
|
||||
func(*args, **kargs)
|
||||
return x
|
||||
|
||||
|
||||
def test_push_pop_1(x, *args, **kargs):
|
||||
"""push_pop_vars in main_function is : `l`, `k`"""
|
||||
l = []
|
||||
k = []
|
||||
for i in range(10):
|
||||
l.append(i)
|
||||
k.pop(i)
|
||||
return l
|
||||
|
||||
|
||||
def test_push_pop_2(x, *args, **kargs):
|
||||
"""push_pop_vars in main_function is : `k`"""
|
||||
l = []
|
||||
k = []
|
||||
|
||||
def func():
|
||||
l.append(0)
|
||||
|
||||
for i in range(10):
|
||||
k.append(i)
|
||||
return l, k
|
||||
|
||||
|
||||
def test_push_pop_3(x, *args, **kargs):
|
||||
"""push_pop_vars in main_function is : `k`
|
||||
NOTE: One may expect `k` and `l` because l
|
||||
is nonlocal. Name bind analysis is
|
||||
not implemented yet.
|
||||
"""
|
||||
l = []
|
||||
k = []
|
||||
|
||||
def func():
|
||||
nonlocal l
|
||||
l.append(0)
|
||||
|
||||
for i in range(10):
|
||||
k.append(i)
|
||||
return l, k
|
||||
|
||||
|
||||
def test_push_pop_4(x, *args, **kargs):
|
||||
"""push_pop_vars in main_function is : `k`"""
|
||||
l = []
|
||||
k = []
|
||||
for i in range(10):
|
||||
for j in range(10):
|
||||
if True:
|
||||
l.append(j)
|
||||
else:
|
||||
k.pop()
|
||||
return l, k
|
||||
|
||||
|
||||
class TestClosureAnalysis(Dy2StTestBase):
|
||||
def setUp(self):
|
||||
self.judge_type = "var and w_vars"
|
||||
self.init_dygraph_func()
|
||||
|
||||
def init_dygraph_func(self):
|
||||
self.all_dygraph_funcs = [
|
||||
test_nonlocal,
|
||||
test_global,
|
||||
test_normal_0,
|
||||
test_normal_argument,
|
||||
]
|
||||
self.answer = [
|
||||
{'func': set('k'), 'test_nonlocal': set('i')},
|
||||
{
|
||||
'func': set({'i'}),
|
||||
},
|
||||
{
|
||||
'func': set('i'),
|
||||
},
|
||||
{
|
||||
'func': set('i'),
|
||||
},
|
||||
]
|
||||
|
||||
self.modified_var = [
|
||||
{'func': set('ki'), 'test_nonlocal': set('i')},
|
||||
{'func': set({'i'}), 'test_global': set({"t"})},
|
||||
{
|
||||
'func': set('i'),
|
||||
},
|
||||
{'func': set('i'), 'test_normal_argument': set('x')},
|
||||
]
|
||||
|
||||
def test_main(self):
|
||||
if self.judge_type == 'push_pop_vars':
|
||||
for push_pop_vars, func in zip(
|
||||
self.push_pop_vars, self.all_dygraph_funcs
|
||||
):
|
||||
test_func = inspect.getsource(func)
|
||||
gast_root = gast.parse(test_func)
|
||||
name_visitor = FunctionNameLivenessAnalysis(gast_root)
|
||||
JudgePushPopVisitor(push_pop_vars).visit(gast_root)
|
||||
else:
|
||||
for mod, ans, func in zip(
|
||||
self.modified_var, self.answer, self.all_dygraph_funcs
|
||||
):
|
||||
test_func = inspect.getsource(func)
|
||||
gast_root = gast.parse(test_func)
|
||||
name_visitor = FunctionNameLivenessAnalysis(gast_root)
|
||||
JudgeVisitor(ans, mod).visit(gast_root)
|
||||
|
||||
|
||||
def TestClosureAnalysis_Attribute_func():
|
||||
# in this function, only self is a Name, self.current is a Attribute. self is read and self.current.function is store()
|
||||
i = 0
|
||||
self.current.function = 12
|
||||
|
||||
|
||||
class TestClosureAnalysis_Attribute(TestClosureAnalysis):
|
||||
def init_dygraph_func(self):
|
||||
self.all_dygraph_funcs = [TestClosureAnalysis_Attribute_func]
|
||||
self.answer = [{"TestClosureAnalysis_Attribute_func": set({'i'})}]
|
||||
self.modified_var = [
|
||||
{
|
||||
"TestClosureAnalysis_Attribute_func": set(
|
||||
{'i', 'self.current.function'}
|
||||
)
|
||||
}
|
||||
]
|
||||
|
||||
|
||||
class TestClosureAnalysis_PushPop(TestClosureAnalysis):
|
||||
def init_dygraph_func(self):
|
||||
self.judge_type = "push_pop_vars"
|
||||
self.all_dygraph_funcs = [
|
||||
test_push_pop_1,
|
||||
test_push_pop_2,
|
||||
test_push_pop_3,
|
||||
test_push_pop_4,
|
||||
]
|
||||
self.push_pop_vars = [
|
||||
{
|
||||
"test_push_pop_1": set({'l', 'k'}),
|
||||
},
|
||||
{
|
||||
"test_push_pop_2": set({'k'}),
|
||||
"func": set("l"),
|
||||
},
|
||||
{
|
||||
"test_push_pop_3": set({'k'}),
|
||||
"func": set("l"),
|
||||
},
|
||||
{
|
||||
"test_push_pop_4": set({'k', 'l'}),
|
||||
},
|
||||
]
|
||||
|
||||
|
||||
class TestPushPopTrans(Dy2StTestBase):
|
||||
def test(self):
|
||||
def vlist_of_dict(x):
|
||||
ma = {'a': []}
|
||||
for i in range(3):
|
||||
ma['a'].append(1)
|
||||
return ma
|
||||
|
||||
x = paddle.to_tensor([3])
|
||||
print(paddle.jit.to_static(vlist_of_dict)(x))
|
||||
|
||||
def test2(self):
|
||||
def vlist_of_dict(x):
|
||||
a = np.array([1, 2, 3])
|
||||
for i in range(3):
|
||||
np.append(a, 4)
|
||||
return a
|
||||
|
||||
x = paddle.to_tensor([3])
|
||||
print(paddle.jit.to_static(vlist_of_dict)(x))
|
||||
|
||||
def test3(self):
|
||||
def vlist_of_dict(x):
|
||||
a = np.array([1, 2, 3])
|
||||
if True:
|
||||
pass
|
||||
return a
|
||||
|
||||
x = paddle.to_tensor([3])
|
||||
print(paddle.jit.to_static(vlist_of_dict)(x))
|
||||
|
||||
def test4(self):
|
||||
def vlist_of_dict(x):
|
||||
a = np.array([1, 2, 3])
|
||||
for i in range(3):
|
||||
append(a, 4)
|
||||
return a
|
||||
|
||||
x = paddle.to_tensor([3])
|
||||
print(paddle.jit.to_static(vlist_of_dict)(x))
|
||||
|
||||
def test5(self):
|
||||
def vlist_of_dict(x):
|
||||
a = np.array([1, 2, 3])
|
||||
for i in range(3):
|
||||
global_a.append(4)
|
||||
return a
|
||||
|
||||
x = paddle.to_tensor([3])
|
||||
print(paddle.jit.to_static(vlist_of_dict)(x))
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
||||
Reference in New Issue
Block a user