blob: 913f805e12a73e4c2fcba76b77184666fe9a3690 [file] [log] [blame]
Raymond Hettingerfd2d1f72004-08-23 23:37:48 +00001import dis
2import sys
3from cStringIO import StringIO
4import unittest
5
6def disassemble(func):
7 f = StringIO()
8 tmp = sys.stdout
9 sys.stdout = f
10 dis.dis(func)
11 sys.stdout = tmp
12 result = f.getvalue()
13 f.close()
14 return result
15
16def dis_single(line):
17 return disassemble(compile(line, '', 'single'))
18
19class TestTranforms(unittest.TestCase):
20
21 def test_unot(self):
22 # UNARY_NOT JUMP_IF_FALSE POP_TOP --> JUMP_IF_TRUE POP_TOP'
23 def unot(x):
24 if not x == 2:
25 del x
26 asm = disassemble(unot)
27 for elem in ('UNARY_NOT', 'JUMP_IF_FALSE'):
28 self.assert_(elem not in asm)
29 for elem in ('JUMP_IF_TRUE', 'POP_TOP'):
30 self.assert_(elem in asm)
31
32 def test_elim_inversion_of_is_or_in(self):
33 for line, elem in (
34 ('not a is b', '(is not)',),
35 ('not a in b', '(not in)',),
36 ('not a is not b', '(is)',),
37 ('not a not in b', '(in)',),
38 ):
39 asm = dis_single(line)
40 self.assert_(elem in asm)
41
42 def test_none_as_constant(self):
43 # LOAD_GLOBAL None --> LOAD_CONST None
44 def f(x):
Tim Peters66cb0182004-08-26 05:23:19 +000045 None
46 return x
Raymond Hettingerfd2d1f72004-08-23 23:37:48 +000047 asm = disassemble(f)
48 for elem in ('LOAD_GLOBAL',):
49 self.assert_(elem not in asm)
50 for elem in ('LOAD_CONST', '(None)'):
51 self.assert_(elem in asm)
52
53 def test_while_one(self):
54 # Skip over: LOAD_CONST trueconst JUMP_IF_FALSE xx POP_TOP
55 def f():
Tim Peters66cb0182004-08-26 05:23:19 +000056 while 1:
57 pass
58 return list
Raymond Hettingerfd2d1f72004-08-23 23:37:48 +000059 asm = disassemble(f)
60 for elem in ('LOAD_CONST', 'JUMP_IF_FALSE'):
61 self.assert_(elem not in asm)
62 for elem in ('JUMP_ABSOLUTE',):
63 self.assert_(elem in asm)
64
65 def test_pack_unpack(self):
66 for line, elem in (
Raymond Hettinger2c31a052004-09-22 18:44:21 +000067 ('a, = a,', 'LOAD_CONST',),
68 ('a, b = a, b', 'ROT_TWO',),
69 ('a, b, c = a, b, c', 'ROT_THREE',),
Raymond Hettingerfd2d1f72004-08-23 23:37:48 +000070 ):
71 asm = dis_single(line)
72 self.assert_(elem in asm)
73 self.assert_('BUILD_TUPLE' not in asm)
74 self.assert_('UNPACK_TUPLE' not in asm)
75
Raymond Hettinger2c31a052004-09-22 18:44:21 +000076 def test_folding_of_tuples_of_constants(self):
77 for line, elem in (
78 ('a = 1,2,3', '((1, 2, 3))',),
79 ('("a","b","c")', "(('a', 'b', 'c'))",),
80 ('a,b,c = 1,2,3', '((1, 2, 3))',),
81 ):
82 asm = dis_single(line)
83 self.assert_(elem in asm)
84 self.assert_('BUILD_TUPLE' not in asm)
85
Raymond Hettingerfd2d1f72004-08-23 23:37:48 +000086 def test_elim_extra_return(self):
87 # RETURN LOAD_CONST None RETURN --> RETURN
88 def f(x):
89 return x
90 asm = disassemble(f)
91 self.assert_('LOAD_CONST' not in asm)
92 self.assert_('(None)' not in asm)
93 self.assertEqual(asm.split().count('RETURN_VALUE'), 1)
94
95
96
97def test_main(verbose=None):
98 import sys
99 from test import test_support
100 test_classes = (TestTranforms,)
101 test_support.run_unittest(*test_classes)
102
103 # verify reference counting
104 if verbose and hasattr(sys, "gettotalrefcount"):
105 import gc
106 counts = [None] * 5
107 for i in xrange(len(counts)):
108 test_support.run_unittest(*test_classes)
109 gc.collect()
110 counts[i] = sys.gettotalrefcount()
111 print counts
112
113if __name__ == "__main__":
114 test_main(verbose=True)