1import ast
2import builtins
3import dis
4import enum
5import os
6import sys
7import types
8import unittest
9import warnings
10import weakref
11from textwrap import dedent
12
13from test import support
14
15def to_tuple(t):
16    if t is None or isinstance(t, (str, int, complex)) or t is Ellipsis:
17        return t
18    elif isinstance(t, list):
19        return [to_tuple(e) for e in t]
20    result = [t.__class__.__name__]
21    if hasattr(t, 'lineno') and hasattr(t, 'col_offset'):
22        result.append((t.lineno, t.col_offset))
23        if hasattr(t, 'end_lineno') and hasattr(t, 'end_col_offset'):
24            result[-1] += (t.end_lineno, t.end_col_offset)
25    if t._fields is None:
26        return tuple(result)
27    for f in t._fields:
28        result.append(to_tuple(getattr(t, f)))
29    return tuple(result)
30
31
32# These tests are compiled through "exec"
33# There should be at least one test per statement
34exec_tests = [
35    # None
36    "None",
37    # Module docstring
38    "'module docstring'",
39    # FunctionDef
40    "def f(): pass",
41    # FunctionDef with docstring
42    "def f(): 'function docstring'",
43    # FunctionDef with arg
44    "def f(a): pass",
45    # FunctionDef with arg and default value
46    "def f(a=0): pass",
47    # FunctionDef with varargs
48    "def f(*args): pass",
49    # FunctionDef with varargs as TypeVarTuple
50    "def f(*args: *Ts): pass",
51    # FunctionDef with varargs as unpacked Tuple
52    "def f(*args: *tuple[int, ...]): pass",
53    # FunctionDef with varargs as unpacked Tuple *and* TypeVarTuple
54    "def f(*args: *tuple[int, *Ts]): pass",
55    # FunctionDef with kwargs
56    "def f(**kwargs): pass",
57    # FunctionDef with all kind of args and docstring
58    "def f(a, b=1, c=None, d=[], e={}, *args, f=42, **kwargs): 'doc for f()'",
59    # FunctionDef with type annotation on return involving unpacking
60    "def f() -> tuple[*Ts]: pass",
61    "def f() -> tuple[int, *Ts]: pass",
62    "def f() -> tuple[int, *tuple[int, ...]]: pass",
63    # ClassDef
64    "class C:pass",
65    # ClassDef with docstring
66    "class C: 'docstring for class C'",
67    # ClassDef, new style class
68    "class C(object): pass",
69    # Return
70    "def f():return 1",
71    # Delete
72    "del v",
73    # Assign
74    "v = 1",
75    "a,b = c",
76    "(a,b) = c",
77    "[a,b] = c",
78    # AnnAssign with unpacked types
79    "x: tuple[*Ts]",
80    "x: tuple[int, *Ts]",
81    "x: tuple[int, *tuple[str, ...]]",
82    # AugAssign
83    "v += 1",
84    # For
85    "for v in v:pass",
86    # While
87    "while v:pass",
88    # If
89    "if v:pass",
90    # If-Elif
91    "if a:\n  pass\nelif b:\n  pass",
92    # If-Elif-Else
93    "if a:\n  pass\nelif b:\n  pass\nelse:\n  pass",
94    # With
95    "with x as y: pass",
96    "with x as y, z as q: pass",
97    # Raise
98    "raise Exception('string')",
99    # TryExcept
100    "try:\n  pass\nexcept Exception:\n  pass",
101    # TryFinally
102    "try:\n  pass\nfinally:\n  pass",
103    # TryStarExcept
104    "try:\n  pass\nexcept* Exception:\n  pass",
105    # Assert
106    "assert v",
107    # Import
108    "import sys",
109    # ImportFrom
110    "from sys import v",
111    # Global
112    "global v",
113    # Expr
114    "1",
115    # Pass,
116    "pass",
117    # Break
118    "for v in v:break",
119    # Continue
120    "for v in v:continue",
121    # for statements with naked tuples (see http://bugs.python.org/issue6704)
122    "for a,b in c: pass",
123    "for (a,b) in c: pass",
124    "for [a,b] in c: pass",
125    # Multiline generator expression (test for .lineno & .col_offset)
126    """(
127    (
128    Aa
129    ,
130       Bb
131    )
132    for
133    Aa
134    ,
135    Bb in Cc
136    )""",
137    # dictcomp
138    "{a : b for w in x for m in p if g}",
139    # dictcomp with naked tuple
140    "{a : b for v,w in x}",
141    # setcomp
142    "{r for l in x if g}",
143    # setcomp with naked tuple
144    "{r for l,m in x}",
145    # AsyncFunctionDef
146    "async def f():\n 'async function'\n await something()",
147    # AsyncFor
148    "async def f():\n async for e in i: 1\n else: 2",
149    # AsyncWith
150    "async def f():\n async with a as b: 1",
151    # PEP 448: Additional Unpacking Generalizations
152    "{**{1:2}, 2:3}",
153    "{*{1, 2}, 3}",
154    # Asynchronous comprehensions
155    "async def f():\n [i async for b in c]",
156    # Decorated FunctionDef
157    "@deco1\n@deco2()\n@deco3(1)\ndef f(): pass",
158    # Decorated AsyncFunctionDef
159    "@deco1\n@deco2()\n@deco3(1)\nasync def f(): pass",
160    # Decorated ClassDef
161    "@deco1\n@deco2()\n@deco3(1)\nclass C: pass",
162    # Decorator with generator argument
163    "@deco(a for a in b)\ndef f(): pass",
164    # Decorator with attribute
165    "@a.b.c\ndef f(): pass",
166    # Simple assignment expression
167    "(a := 1)",
168    # Positional-only arguments
169    "def f(a, /,): pass",
170    "def f(a, /, c, d, e): pass",
171    "def f(a, /, c, *, d, e): pass",
172    "def f(a, /, c, *, d, e, **kwargs): pass",
173    # Positional-only arguments with defaults
174    "def f(a=1, /,): pass",
175    "def f(a=1, /, b=2, c=4): pass",
176    "def f(a=1, /, b=2, *, c=4): pass",
177    "def f(a=1, /, b=2, *, c): pass",
178    "def f(a=1, /, b=2, *, c=4, **kwargs): pass",
179    "def f(a=1, /, b=2, *, c, **kwargs): pass",
180
181]
182
183# These are compiled through "single"
184# because of overlap with "eval", it just tests what
185# can't be tested with "eval"
186single_tests = [
187    "1+2"
188]
189
190# These are compiled through "eval"
191# It should test all expressions
192eval_tests = [
193  # None
194  "None",
195  # BoolOp
196  "a and b",
197  # BinOp
198  "a + b",
199  # UnaryOp
200  "not v",
201  # Lambda
202  "lambda:None",
203  # Dict
204  "{ 1:2 }",
205  # Empty dict
206  "{}",
207  # Set
208  "{None,}",
209  # Multiline dict (test for .lineno & .col_offset)
210  """{
211      1
212        :
213          2
214     }""",
215  # ListComp
216  "[a for b in c if d]",
217  # GeneratorExp
218  "(a for b in c if d)",
219  # Comprehensions with multiple for targets
220  "[(a,b) for a,b in c]",
221  "[(a,b) for (a,b) in c]",
222  "[(a,b) for [a,b] in c]",
223  "{(a,b) for a,b in c}",
224  "{(a,b) for (a,b) in c}",
225  "{(a,b) for [a,b] in c}",
226  "((a,b) for a,b in c)",
227  "((a,b) for (a,b) in c)",
228  "((a,b) for [a,b] in c)",
229  # Yield - yield expressions can't work outside a function
230  #
231  # Compare
232  "1 < 2 < 3",
233  # Call
234  "f(1,2,c=3,*d,**e)",
235  # Call with multi-character starred
236  "f(*[0, 1])",
237  # Call with a generator argument
238  "f(a for a in b)",
239  # Num
240  "10",
241  # Str
242  "'string'",
243  # Attribute
244  "a.b",
245  # Subscript
246  "a[b:c]",
247  # Name
248  "v",
249  # List
250  "[1,2,3]",
251  # Empty list
252  "[]",
253  # Tuple
254  "1,2,3",
255  # Tuple
256  "(1,2,3)",
257  # Empty tuple
258  "()",
259  # Combination
260  "a.b.c.d(a.b[1:2])",
261
262]
263
264# TODO: expr_context, slice, boolop, operator, unaryop, cmpop, comprehension
265# excepthandler, arguments, keywords, alias
266
267class AST_Tests(unittest.TestCase):
268
269    def _is_ast_node(self, name, node):
270        if not isinstance(node, type):
271            return False
272        if "ast" not in node.__module__:
273            return False
274        return name != 'AST' and name[0].isupper()
275
276    def _assertTrueorder(self, ast_node, parent_pos):
277        if not isinstance(ast_node, ast.AST) or ast_node._fields is None:
278            return
279        if isinstance(ast_node, (ast.expr, ast.stmt, ast.excepthandler)):
280            node_pos = (ast_node.lineno, ast_node.col_offset)
281            self.assertGreaterEqual(node_pos, parent_pos)
282            parent_pos = (ast_node.lineno, ast_node.col_offset)
283        for name in ast_node._fields:
284            value = getattr(ast_node, name)
285            if isinstance(value, list):
286                first_pos = parent_pos
287                if value and name == 'decorator_list':
288                    first_pos = (value[0].lineno, value[0].col_offset)
289                for child in value:
290                    self._assertTrueorder(child, first_pos)
291            elif value is not None:
292                self._assertTrueorder(value, parent_pos)
293        self.assertEqual(ast_node._fields, ast_node.__match_args__)
294
295    def test_AST_objects(self):
296        x = ast.AST()
297        self.assertEqual(x._fields, ())
298        x.foobar = 42
299        self.assertEqual(x.foobar, 42)
300        self.assertEqual(x.__dict__["foobar"], 42)
301
302        with self.assertRaises(AttributeError):
303            x.vararg
304
305        with self.assertRaises(TypeError):
306            # "ast.AST constructor takes 0 positional arguments"
307            ast.AST(2)
308
309    def test_AST_garbage_collection(self):
310        class X:
311            pass
312        a = ast.AST()
313        a.x = X()
314        a.x.a = a
315        ref = weakref.ref(a.x)
316        del a
317        support.gc_collect()
318        self.assertIsNone(ref())
319
320    def test_snippets(self):
321        for input, output, kind in ((exec_tests, exec_results, "exec"),
322                                    (single_tests, single_results, "single"),
323                                    (eval_tests, eval_results, "eval")):
324            for i, o in zip(input, output):
325                with self.subTest(action="parsing", input=i):
326                    ast_tree = compile(i, "?", kind, ast.PyCF_ONLY_AST)
327                    self.assertEqual(to_tuple(ast_tree), o)
328                    self._assertTrueorder(ast_tree, (0, 0))
329                with self.subTest(action="compiling", input=i, kind=kind):
330                    compile(ast_tree, "?", kind)
331
332    def test_ast_validation(self):
333        # compile() is the only function that calls PyAST_Validate
334        snippets_to_validate = exec_tests + single_tests + eval_tests
335        for snippet in snippets_to_validate:
336            tree = ast.parse(snippet)
337            compile(tree, '<string>', 'exec')
338
339    def test_invalid_position_information(self):
340        invalid_linenos = [
341            (10, 1), (-10, -11), (10, -11), (-5, -2), (-5, 1)
342        ]
343
344        for lineno, end_lineno in invalid_linenos:
345            with self.subTest(f"Check invalid linenos {lineno}:{end_lineno}"):
346                snippet = "a = 1"
347                tree = ast.parse(snippet)
348                tree.body[0].lineno = lineno
349                tree.body[0].end_lineno = end_lineno
350                with self.assertRaises(ValueError):
351                    compile(tree, '<string>', 'exec')
352
353        invalid_col_offsets = [
354            (10, 1), (-10, -11), (10, -11), (-5, -2), (-5, 1)
355        ]
356        for col_offset, end_col_offset in invalid_col_offsets:
357            with self.subTest(f"Check invalid col_offset {col_offset}:{end_col_offset}"):
358                snippet = "a = 1"
359                tree = ast.parse(snippet)
360                tree.body[0].col_offset = col_offset
361                tree.body[0].end_col_offset = end_col_offset
362                with self.assertRaises(ValueError):
363                    compile(tree, '<string>', 'exec')
364
365    def test_compilation_of_ast_nodes_with_default_end_position_values(self):
366        tree = ast.Module(body=[
367            ast.Import(names=[ast.alias(name='builtins', lineno=1, col_offset=0)], lineno=1, col_offset=0),
368            ast.Import(names=[ast.alias(name='traceback', lineno=0, col_offset=0)], lineno=0, col_offset=1)
369        ], type_ignores=[])
370
371        # Check that compilation doesn't crash. Note: this may crash explicitly only on debug mode.
372        compile(tree, "<string>", "exec")
373
374    def test_slice(self):
375        slc = ast.parse("x[::]").body[0].value.slice
376        self.assertIsNone(slc.upper)
377        self.assertIsNone(slc.lower)
378        self.assertIsNone(slc.step)
379
380    def test_from_import(self):
381        im = ast.parse("from . import y").body[0]
382        self.assertIsNone(im.module)
383
384    def test_non_interned_future_from_ast(self):
385        mod = ast.parse("from __future__ import division")
386        self.assertIsInstance(mod.body[0], ast.ImportFrom)
387        mod.body[0].module = " __future__ ".strip()
388        compile(mod, "<test>", "exec")
389
390    def test_alias(self):
391        im = ast.parse("from bar import y").body[0]
392        self.assertEqual(len(im.names), 1)
393        alias = im.names[0]
394        self.assertEqual(alias.name, 'y')
395        self.assertIsNone(alias.asname)
396        self.assertEqual(alias.lineno, 1)
397        self.assertEqual(alias.end_lineno, 1)
398        self.assertEqual(alias.col_offset, 16)
399        self.assertEqual(alias.end_col_offset, 17)
400
401        im = ast.parse("from bar import *").body[0]
402        alias = im.names[0]
403        self.assertEqual(alias.name, '*')
404        self.assertIsNone(alias.asname)
405        self.assertEqual(alias.lineno, 1)
406        self.assertEqual(alias.end_lineno, 1)
407        self.assertEqual(alias.col_offset, 16)
408        self.assertEqual(alias.end_col_offset, 17)
409
410        im = ast.parse("from bar import y as z").body[0]
411        alias = im.names[0]
412        self.assertEqual(alias.name, "y")
413        self.assertEqual(alias.asname, "z")
414        self.assertEqual(alias.lineno, 1)
415        self.assertEqual(alias.end_lineno, 1)
416        self.assertEqual(alias.col_offset, 16)
417        self.assertEqual(alias.end_col_offset, 22)
418
419        im = ast.parse("import bar as foo").body[0]
420        alias = im.names[0]
421        self.assertEqual(alias.name, "bar")
422        self.assertEqual(alias.asname, "foo")
423        self.assertEqual(alias.lineno, 1)
424        self.assertEqual(alias.end_lineno, 1)
425        self.assertEqual(alias.col_offset, 7)
426        self.assertEqual(alias.end_col_offset, 17)
427
428    def test_base_classes(self):
429        self.assertTrue(issubclass(ast.For, ast.stmt))
430        self.assertTrue(issubclass(ast.Name, ast.expr))
431        self.assertTrue(issubclass(ast.stmt, ast.AST))
432        self.assertTrue(issubclass(ast.expr, ast.AST))
433        self.assertTrue(issubclass(ast.comprehension, ast.AST))
434        self.assertTrue(issubclass(ast.Gt, ast.AST))
435
436    def test_field_attr_existence(self):
437        for name, item in ast.__dict__.items():
438            if self._is_ast_node(name, item):
439                if name == 'Index':
440                    # Index(value) just returns value now.
441                    # The argument is required.
442                    continue
443                x = item()
444                if isinstance(x, ast.AST):
445                    self.assertEqual(type(x._fields), tuple)
446
447    def test_arguments(self):
448        x = ast.arguments()
449        self.assertEqual(x._fields, ('posonlyargs', 'args', 'vararg', 'kwonlyargs',
450                                     'kw_defaults', 'kwarg', 'defaults'))
451
452        with self.assertRaises(AttributeError):
453            x.args
454        self.assertIsNone(x.vararg)
455
456        x = ast.arguments(*range(1, 8))
457        self.assertEqual(x.args, 2)
458        self.assertEqual(x.vararg, 3)
459
460    def test_field_attr_writable(self):
461        x = ast.Num()
462        # We can assign to _fields
463        x._fields = 666
464        self.assertEqual(x._fields, 666)
465
466    def test_classattrs(self):
467        x = ast.Num()
468        self.assertEqual(x._fields, ('value', 'kind'))
469
470        with self.assertRaises(AttributeError):
471            x.value
472
473        with self.assertRaises(AttributeError):
474            x.n
475
476        x = ast.Num(42)
477        self.assertEqual(x.value, 42)
478        self.assertEqual(x.n, 42)
479
480        with self.assertRaises(AttributeError):
481            x.lineno
482
483        with self.assertRaises(AttributeError):
484            x.foobar
485
486        x = ast.Num(lineno=2)
487        self.assertEqual(x.lineno, 2)
488
489        x = ast.Num(42, lineno=0)
490        self.assertEqual(x.lineno, 0)
491        self.assertEqual(x._fields, ('value', 'kind'))
492        self.assertEqual(x.value, 42)
493        self.assertEqual(x.n, 42)
494
495        self.assertRaises(TypeError, ast.Num, 1, None, 2)
496        self.assertRaises(TypeError, ast.Num, 1, None, 2, lineno=0)
497
498        # Arbitrary keyword arguments are supported
499        self.assertEqual(ast.Constant(1, foo='bar').foo, 'bar')
500        self.assertEqual(ast.Num(1, foo='bar').foo, 'bar')
501
502        with self.assertRaisesRegex(TypeError, "Num got multiple values for argument 'n'"):
503            ast.Num(1, n=2)
504        with self.assertRaisesRegex(TypeError, "Constant got multiple values for argument 'value'"):
505            ast.Constant(1, value=2)
506
507        self.assertEqual(ast.Num(42).n, 42)
508        self.assertEqual(ast.Num(4.25).n, 4.25)
509        self.assertEqual(ast.Num(4.25j).n, 4.25j)
510        self.assertEqual(ast.Str('42').s, '42')
511        self.assertEqual(ast.Bytes(b'42').s, b'42')
512        self.assertIs(ast.NameConstant(True).value, True)
513        self.assertIs(ast.NameConstant(False).value, False)
514        self.assertIs(ast.NameConstant(None).value, None)
515
516        self.assertEqual(ast.Constant(42).value, 42)
517        self.assertEqual(ast.Constant(4.25).value, 4.25)
518        self.assertEqual(ast.Constant(4.25j).value, 4.25j)
519        self.assertEqual(ast.Constant('42').value, '42')
520        self.assertEqual(ast.Constant(b'42').value, b'42')
521        self.assertIs(ast.Constant(True).value, True)
522        self.assertIs(ast.Constant(False).value, False)
523        self.assertIs(ast.Constant(None).value, None)
524        self.assertIs(ast.Constant(...).value, ...)
525
526    def test_realtype(self):
527        self.assertEqual(type(ast.Num(42)), ast.Constant)
528        self.assertEqual(type(ast.Num(4.25)), ast.Constant)
529        self.assertEqual(type(ast.Num(4.25j)), ast.Constant)
530        self.assertEqual(type(ast.Str('42')), ast.Constant)
531        self.assertEqual(type(ast.Bytes(b'42')), ast.Constant)
532        self.assertEqual(type(ast.NameConstant(True)), ast.Constant)
533        self.assertEqual(type(ast.NameConstant(False)), ast.Constant)
534        self.assertEqual(type(ast.NameConstant(None)), ast.Constant)
535        self.assertEqual(type(ast.Ellipsis()), ast.Constant)
536
537    def test_isinstance(self):
538        self.assertTrue(isinstance(ast.Num(42), ast.Num))
539        self.assertTrue(isinstance(ast.Num(4.2), ast.Num))
540        self.assertTrue(isinstance(ast.Num(4.2j), ast.Num))
541        self.assertTrue(isinstance(ast.Str('42'), ast.Str))
542        self.assertTrue(isinstance(ast.Bytes(b'42'), ast.Bytes))
543        self.assertTrue(isinstance(ast.NameConstant(True), ast.NameConstant))
544        self.assertTrue(isinstance(ast.NameConstant(False), ast.NameConstant))
545        self.assertTrue(isinstance(ast.NameConstant(None), ast.NameConstant))
546        self.assertTrue(isinstance(ast.Ellipsis(), ast.Ellipsis))
547
548        self.assertTrue(isinstance(ast.Constant(42), ast.Num))
549        self.assertTrue(isinstance(ast.Constant(4.2), ast.Num))
550        self.assertTrue(isinstance(ast.Constant(4.2j), ast.Num))
551        self.assertTrue(isinstance(ast.Constant('42'), ast.Str))
552        self.assertTrue(isinstance(ast.Constant(b'42'), ast.Bytes))
553        self.assertTrue(isinstance(ast.Constant(True), ast.NameConstant))
554        self.assertTrue(isinstance(ast.Constant(False), ast.NameConstant))
555        self.assertTrue(isinstance(ast.Constant(None), ast.NameConstant))
556        self.assertTrue(isinstance(ast.Constant(...), ast.Ellipsis))
557
558        self.assertFalse(isinstance(ast.Str('42'), ast.Num))
559        self.assertFalse(isinstance(ast.Num(42), ast.Str))
560        self.assertFalse(isinstance(ast.Str('42'), ast.Bytes))
561        self.assertFalse(isinstance(ast.Num(42), ast.NameConstant))
562        self.assertFalse(isinstance(ast.Num(42), ast.Ellipsis))
563        self.assertFalse(isinstance(ast.NameConstant(True), ast.Num))
564        self.assertFalse(isinstance(ast.NameConstant(False), ast.Num))
565
566        self.assertFalse(isinstance(ast.Constant('42'), ast.Num))
567        self.assertFalse(isinstance(ast.Constant(42), ast.Str))
568        self.assertFalse(isinstance(ast.Constant('42'), ast.Bytes))
569        self.assertFalse(isinstance(ast.Constant(42), ast.NameConstant))
570        self.assertFalse(isinstance(ast.Constant(42), ast.Ellipsis))
571        self.assertFalse(isinstance(ast.Constant(True), ast.Num))
572        self.assertFalse(isinstance(ast.Constant(False), ast.Num))
573
574        self.assertFalse(isinstance(ast.Constant(), ast.Num))
575        self.assertFalse(isinstance(ast.Constant(), ast.Str))
576        self.assertFalse(isinstance(ast.Constant(), ast.Bytes))
577        self.assertFalse(isinstance(ast.Constant(), ast.NameConstant))
578        self.assertFalse(isinstance(ast.Constant(), ast.Ellipsis))
579
580        class S(str): pass
581        self.assertTrue(isinstance(ast.Constant(S('42')), ast.Str))
582        self.assertFalse(isinstance(ast.Constant(S('42')), ast.Num))
583
584    def test_subclasses(self):
585        class N(ast.Num):
586            def __init__(self, *args, **kwargs):
587                super().__init__(*args, **kwargs)
588                self.z = 'spam'
589        class N2(ast.Num):
590            pass
591
592        n = N(42)
593        self.assertEqual(n.n, 42)
594        self.assertEqual(n.z, 'spam')
595        self.assertEqual(type(n), N)
596        self.assertTrue(isinstance(n, N))
597        self.assertTrue(isinstance(n, ast.Num))
598        self.assertFalse(isinstance(n, N2))
599        self.assertFalse(isinstance(ast.Num(42), N))
600        n = N(n=42)
601        self.assertEqual(n.n, 42)
602        self.assertEqual(type(n), N)
603
604    def test_module(self):
605        body = [ast.Num(42)]
606        x = ast.Module(body, [])
607        self.assertEqual(x.body, body)
608
609    def test_nodeclasses(self):
610        # Zero arguments constructor explicitly allowed
611        x = ast.BinOp()
612        self.assertEqual(x._fields, ('left', 'op', 'right'))
613
614        # Random attribute allowed too
615        x.foobarbaz = 5
616        self.assertEqual(x.foobarbaz, 5)
617
618        n1 = ast.Num(1)
619        n3 = ast.Num(3)
620        addop = ast.Add()
621        x = ast.BinOp(n1, addop, n3)
622        self.assertEqual(x.left, n1)
623        self.assertEqual(x.op, addop)
624        self.assertEqual(x.right, n3)
625
626        x = ast.BinOp(1, 2, 3)
627        self.assertEqual(x.left, 1)
628        self.assertEqual(x.op, 2)
629        self.assertEqual(x.right, 3)
630
631        x = ast.BinOp(1, 2, 3, lineno=0)
632        self.assertEqual(x.left, 1)
633        self.assertEqual(x.op, 2)
634        self.assertEqual(x.right, 3)
635        self.assertEqual(x.lineno, 0)
636
637        # node raises exception when given too many arguments
638        self.assertRaises(TypeError, ast.BinOp, 1, 2, 3, 4)
639        # node raises exception when given too many arguments
640        self.assertRaises(TypeError, ast.BinOp, 1, 2, 3, 4, lineno=0)
641
642        # can set attributes through kwargs too
643        x = ast.BinOp(left=1, op=2, right=3, lineno=0)
644        self.assertEqual(x.left, 1)
645        self.assertEqual(x.op, 2)
646        self.assertEqual(x.right, 3)
647        self.assertEqual(x.lineno, 0)
648
649        # Random kwargs also allowed
650        x = ast.BinOp(1, 2, 3, foobarbaz=42)
651        self.assertEqual(x.foobarbaz, 42)
652
653    def test_no_fields(self):
654        # this used to fail because Sub._fields was None
655        x = ast.Sub()
656        self.assertEqual(x._fields, ())
657
658    def test_pickling(self):
659        import pickle
660        mods = [pickle]
661        try:
662            import cPickle
663            mods.append(cPickle)
664        except ImportError:
665            pass
666        protocols = [0, 1, 2]
667        for mod in mods:
668            for protocol in protocols:
669                for ast in (compile(i, "?", "exec", 0x400) for i in exec_tests):
670                    ast2 = mod.loads(mod.dumps(ast, protocol))
671                    self.assertEqual(to_tuple(ast2), to_tuple(ast))
672
673    def test_invalid_sum(self):
674        pos = dict(lineno=2, col_offset=3)
675        m = ast.Module([ast.Expr(ast.expr(**pos), **pos)], [])
676        with self.assertRaises(TypeError) as cm:
677            compile(m, "<test>", "exec")
678        self.assertIn("but got <ast.expr", str(cm.exception))
679
680    def test_invalid_identifier(self):
681        m = ast.Module([ast.Expr(ast.Name(42, ast.Load()))], [])
682        ast.fix_missing_locations(m)
683        with self.assertRaises(TypeError) as cm:
684            compile(m, "<test>", "exec")
685        self.assertIn("identifier must be of type str", str(cm.exception))
686
687    def test_invalid_constant(self):
688        for invalid_constant in int, (1, 2, int), frozenset((1, 2, int)):
689            e = ast.Expression(body=ast.Constant(invalid_constant))
690            ast.fix_missing_locations(e)
691            with self.assertRaisesRegex(
692                TypeError, "invalid type in Constant: type"
693            ):
694                compile(e, "<test>", "eval")
695
696    def test_empty_yield_from(self):
697        # Issue 16546: yield from value is not optional.
698        empty_yield_from = ast.parse("def f():\n yield from g()")
699        empty_yield_from.body[0].body[0].value.value = None
700        with self.assertRaises(ValueError) as cm:
701            compile(empty_yield_from, "<test>", "exec")
702        self.assertIn("field 'value' is required", str(cm.exception))
703
704    @support.cpython_only
705    def test_issue31592(self):
706        # There shouldn't be an assertion failure in case of a bad
707        # unicodedata.normalize().
708        import unicodedata
709        def bad_normalize(*args):
710            return None
711        with support.swap_attr(unicodedata, 'normalize', bad_normalize):
712            self.assertRaises(TypeError, ast.parse, '\u03D5')
713
714    def test_issue18374_binop_col_offset(self):
715        tree = ast.parse('4+5+6+7')
716        parent_binop = tree.body[0].value
717        child_binop = parent_binop.left
718        grandchild_binop = child_binop.left
719        self.assertEqual(parent_binop.col_offset, 0)
720        self.assertEqual(parent_binop.end_col_offset, 7)
721        self.assertEqual(child_binop.col_offset, 0)
722        self.assertEqual(child_binop.end_col_offset, 5)
723        self.assertEqual(grandchild_binop.col_offset, 0)
724        self.assertEqual(grandchild_binop.end_col_offset, 3)
725
726        tree = ast.parse('4+5-\\\n 6-7')
727        parent_binop = tree.body[0].value
728        child_binop = parent_binop.left
729        grandchild_binop = child_binop.left
730        self.assertEqual(parent_binop.col_offset, 0)
731        self.assertEqual(parent_binop.lineno, 1)
732        self.assertEqual(parent_binop.end_col_offset, 4)
733        self.assertEqual(parent_binop.end_lineno, 2)
734
735        self.assertEqual(child_binop.col_offset, 0)
736        self.assertEqual(child_binop.lineno, 1)
737        self.assertEqual(child_binop.end_col_offset, 2)
738        self.assertEqual(child_binop.end_lineno, 2)
739
740        self.assertEqual(grandchild_binop.col_offset, 0)
741        self.assertEqual(grandchild_binop.lineno, 1)
742        self.assertEqual(grandchild_binop.end_col_offset, 3)
743        self.assertEqual(grandchild_binop.end_lineno, 1)
744
745    def test_issue39579_dotted_name_end_col_offset(self):
746        tree = ast.parse('@a.b.c\ndef f(): pass')
747        attr_b = tree.body[0].decorator_list[0].value
748        self.assertEqual(attr_b.end_col_offset, 4)
749
750    def test_ast_asdl_signature(self):
751        self.assertEqual(ast.withitem.__doc__, "withitem(expr context_expr, expr? optional_vars)")
752        self.assertEqual(ast.GtE.__doc__, "GtE")
753        self.assertEqual(ast.Name.__doc__, "Name(identifier id, expr_context ctx)")
754        self.assertEqual(ast.cmpop.__doc__, "cmpop = Eq | NotEq | Lt | LtE | Gt | GtE | Is | IsNot | In | NotIn")
755        expressions = [f"     | {node.__doc__}" for node in ast.expr.__subclasses__()]
756        expressions[0] = f"expr = {ast.expr.__subclasses__()[0].__doc__}"
757        self.assertCountEqual(ast.expr.__doc__.split("\n"), expressions)
758
759    def test_positional_only_feature_version(self):
760        ast.parse('def foo(x, /): ...', feature_version=(3, 8))
761        ast.parse('def bar(x=1, /): ...', feature_version=(3, 8))
762        with self.assertRaises(SyntaxError):
763            ast.parse('def foo(x, /): ...', feature_version=(3, 7))
764        with self.assertRaises(SyntaxError):
765            ast.parse('def bar(x=1, /): ...', feature_version=(3, 7))
766
767        ast.parse('lambda x, /: ...', feature_version=(3, 8))
768        ast.parse('lambda x=1, /: ...', feature_version=(3, 8))
769        with self.assertRaises(SyntaxError):
770            ast.parse('lambda x, /: ...', feature_version=(3, 7))
771        with self.assertRaises(SyntaxError):
772            ast.parse('lambda x=1, /: ...', feature_version=(3, 7))
773
774    def test_parenthesized_with_feature_version(self):
775        ast.parse('with (CtxManager() as example): ...', feature_version=(3, 10))
776        # While advertised as a feature in Python 3.10, this was allowed starting 3.9
777        ast.parse('with (CtxManager() as example): ...', feature_version=(3, 9))
778        with self.assertRaises(SyntaxError):
779            ast.parse('with (CtxManager() as example): ...', feature_version=(3, 8))
780        ast.parse('with CtxManager() as example: ...', feature_version=(3, 8))
781
782    def test_debug_f_string_feature_version(self):
783        ast.parse('f"{x=}"', feature_version=(3, 8))
784        with self.assertRaises(SyntaxError):
785            ast.parse('f"{x=}"', feature_version=(3, 7))
786
787    def test_assignment_expression_feature_version(self):
788        ast.parse('(x := 0)', feature_version=(3, 8))
789        with self.assertRaises(SyntaxError):
790            ast.parse('(x := 0)', feature_version=(3, 7))
791
792    def test_exception_groups_feature_version(self):
793        code = dedent('''
794        try: ...
795        except* Exception: ...
796        ''')
797        ast.parse(code)
798        with self.assertRaises(SyntaxError):
799            ast.parse(code, feature_version=(3, 10))
800
801    def test_constant_as_name(self):
802        for constant in "True", "False", "None":
803            expr = ast.Expression(ast.Name(constant, ast.Load()))
804            ast.fix_missing_locations(expr)
805            with self.assertRaisesRegex(ValueError, f"identifier field can't represent '{constant}' constant"):
806                compile(expr, "<test>", "eval")
807
808    def test_precedence_enum(self):
809        class _Precedence(enum.IntEnum):
810            """Precedence table that originated from python grammar."""
811            NAMED_EXPR = enum.auto()      # <target> := <expr1>
812            TUPLE = enum.auto()           # <expr1>, <expr2>
813            YIELD = enum.auto()           # 'yield', 'yield from'
814            TEST = enum.auto()            # 'if'-'else', 'lambda'
815            OR = enum.auto()              # 'or'
816            AND = enum.auto()             # 'and'
817            NOT = enum.auto()             # 'not'
818            CMP = enum.auto()             # '<', '>', '==', '>=', '<=', '!=',
819                                          # 'in', 'not in', 'is', 'is not'
820            EXPR = enum.auto()
821            BOR = EXPR                    # '|'
822            BXOR = enum.auto()            # '^'
823            BAND = enum.auto()            # '&'
824            SHIFT = enum.auto()           # '<<', '>>'
825            ARITH = enum.auto()           # '+', '-'
826            TERM = enum.auto()            # '*', '@', '/', '%', '//'
827            FACTOR = enum.auto()          # unary '+', '-', '~'
828            POWER = enum.auto()           # '**'
829            AWAIT = enum.auto()           # 'await'
830            ATOM = enum.auto()
831            def next(self):
832                try:
833                    return self.__class__(self + 1)
834                except ValueError:
835                    return self
836        enum._test_simple_enum(_Precedence, ast._Precedence)
837
838    @support.cpython_only
839    def test_ast_recursion_limit(self):
840        fail_depth = sys.getrecursionlimit() * 3
841        crash_depth = sys.getrecursionlimit() * 300
842        success_depth = int(fail_depth * 0.75)
843
844        def check_limit(prefix, repeated):
845            expect_ok = prefix + repeated * success_depth
846            ast.parse(expect_ok)
847            for depth in (fail_depth, crash_depth):
848                broken = prefix + repeated * depth
849                details = "Compiling ({!r} + {!r} * {})".format(
850                            prefix, repeated, depth)
851                with self.assertRaises(RecursionError, msg=details):
852                    with support.infinite_recursion():
853                        ast.parse(broken)
854
855        check_limit("a", "()")
856        check_limit("a", ".b")
857        check_limit("a", "[0]")
858        check_limit("a", "*a")
859
860    def test_null_bytes(self):
861        with self.assertRaises(SyntaxError,
862            msg="source code string cannot contain null bytes"):
863            ast.parse("a\0b")
864
865class ASTHelpers_Test(unittest.TestCase):
866    maxDiff = None
867
868    def test_parse(self):
869        a = ast.parse('foo(1 + 1)')
870        b = compile('foo(1 + 1)', '<unknown>', 'exec', ast.PyCF_ONLY_AST)
871        self.assertEqual(ast.dump(a), ast.dump(b))
872
873    def test_parse_in_error(self):
874        try:
875            1/0
876        except Exception:
877            with self.assertRaises(SyntaxError) as e:
878                ast.literal_eval(r"'\U'")
879            self.assertIsNotNone(e.exception.__context__)
880
881    def test_dump(self):
882        node = ast.parse('spam(eggs, "and cheese")')
883        self.assertEqual(ast.dump(node),
884            "Module(body=[Expr(value=Call(func=Name(id='spam', ctx=Load()), "
885            "args=[Name(id='eggs', ctx=Load()), Constant(value='and cheese')], "
886            "keywords=[]))], type_ignores=[])"
887        )
888        self.assertEqual(ast.dump(node, annotate_fields=False),
889            "Module([Expr(Call(Name('spam', Load()), [Name('eggs', Load()), "
890            "Constant('and cheese')], []))], [])"
891        )
892        self.assertEqual(ast.dump(node, include_attributes=True),
893            "Module(body=[Expr(value=Call(func=Name(id='spam', ctx=Load(), "
894            "lineno=1, col_offset=0, end_lineno=1, end_col_offset=4), "
895            "args=[Name(id='eggs', ctx=Load(), lineno=1, col_offset=5, "
896            "end_lineno=1, end_col_offset=9), Constant(value='and cheese', "
897            "lineno=1, col_offset=11, end_lineno=1, end_col_offset=23)], keywords=[], "
898            "lineno=1, col_offset=0, end_lineno=1, end_col_offset=24), "
899            "lineno=1, col_offset=0, end_lineno=1, end_col_offset=24)], type_ignores=[])"
900        )
901
902    def test_dump_indent(self):
903        node = ast.parse('spam(eggs, "and cheese")')
904        self.assertEqual(ast.dump(node, indent=3), """\
905Module(
906   body=[
907      Expr(
908         value=Call(
909            func=Name(id='spam', ctx=Load()),
910            args=[
911               Name(id='eggs', ctx=Load()),
912               Constant(value='and cheese')],
913            keywords=[]))],
914   type_ignores=[])""")
915        self.assertEqual(ast.dump(node, annotate_fields=False, indent='\t'), """\
916Module(
917\t[
918\t\tExpr(
919\t\t\tCall(
920\t\t\t\tName('spam', Load()),
921\t\t\t\t[
922\t\t\t\t\tName('eggs', Load()),
923\t\t\t\t\tConstant('and cheese')],
924\t\t\t\t[]))],
925\t[])""")
926        self.assertEqual(ast.dump(node, include_attributes=True, indent=3), """\
927Module(
928   body=[
929      Expr(
930         value=Call(
931            func=Name(
932               id='spam',
933               ctx=Load(),
934               lineno=1,
935               col_offset=0,
936               end_lineno=1,
937               end_col_offset=4),
938            args=[
939               Name(
940                  id='eggs',
941                  ctx=Load(),
942                  lineno=1,
943                  col_offset=5,
944                  end_lineno=1,
945                  end_col_offset=9),
946               Constant(
947                  value='and cheese',
948                  lineno=1,
949                  col_offset=11,
950                  end_lineno=1,
951                  end_col_offset=23)],
952            keywords=[],
953            lineno=1,
954            col_offset=0,
955            end_lineno=1,
956            end_col_offset=24),
957         lineno=1,
958         col_offset=0,
959         end_lineno=1,
960         end_col_offset=24)],
961   type_ignores=[])""")
962
963    def test_dump_incomplete(self):
964        node = ast.Raise(lineno=3, col_offset=4)
965        self.assertEqual(ast.dump(node),
966            "Raise()"
967        )
968        self.assertEqual(ast.dump(node, include_attributes=True),
969            "Raise(lineno=3, col_offset=4)"
970        )
971        node = ast.Raise(exc=ast.Name(id='e', ctx=ast.Load()), lineno=3, col_offset=4)
972        self.assertEqual(ast.dump(node),
973            "Raise(exc=Name(id='e', ctx=Load()))"
974        )
975        self.assertEqual(ast.dump(node, annotate_fields=False),
976            "Raise(Name('e', Load()))"
977        )
978        self.assertEqual(ast.dump(node, include_attributes=True),
979            "Raise(exc=Name(id='e', ctx=Load()), lineno=3, col_offset=4)"
980        )
981        self.assertEqual(ast.dump(node, annotate_fields=False, include_attributes=True),
982            "Raise(Name('e', Load()), lineno=3, col_offset=4)"
983        )
984        node = ast.Raise(cause=ast.Name(id='e', ctx=ast.Load()))
985        self.assertEqual(ast.dump(node),
986            "Raise(cause=Name(id='e', ctx=Load()))"
987        )
988        self.assertEqual(ast.dump(node, annotate_fields=False),
989            "Raise(cause=Name('e', Load()))"
990        )
991
992    def test_copy_location(self):
993        src = ast.parse('1 + 1', mode='eval')
994        src.body.right = ast.copy_location(ast.Num(2), src.body.right)
995        self.assertEqual(ast.dump(src, include_attributes=True),
996            'Expression(body=BinOp(left=Constant(value=1, lineno=1, col_offset=0, '
997            'end_lineno=1, end_col_offset=1), op=Add(), right=Constant(value=2, '
998            'lineno=1, col_offset=4, end_lineno=1, end_col_offset=5), lineno=1, '
999            'col_offset=0, end_lineno=1, end_col_offset=5))'
1000        )
1001        src = ast.Call(col_offset=1, lineno=1, end_lineno=1, end_col_offset=1)
1002        new = ast.copy_location(src, ast.Call(col_offset=None, lineno=None))
1003        self.assertIsNone(new.end_lineno)
1004        self.assertIsNone(new.end_col_offset)
1005        self.assertEqual(new.lineno, 1)
1006        self.assertEqual(new.col_offset, 1)
1007
1008    def test_fix_missing_locations(self):
1009        src = ast.parse('write("spam")')
1010        src.body.append(ast.Expr(ast.Call(ast.Name('spam', ast.Load()),
1011                                          [ast.Str('eggs')], [])))
1012        self.assertEqual(src, ast.fix_missing_locations(src))
1013        self.maxDiff = None
1014        self.assertEqual(ast.dump(src, include_attributes=True),
1015            "Module(body=[Expr(value=Call(func=Name(id='write', ctx=Load(), "
1016            "lineno=1, col_offset=0, end_lineno=1, end_col_offset=5), "
1017            "args=[Constant(value='spam', lineno=1, col_offset=6, end_lineno=1, "
1018            "end_col_offset=12)], keywords=[], lineno=1, col_offset=0, end_lineno=1, "
1019            "end_col_offset=13), lineno=1, col_offset=0, end_lineno=1, "
1020            "end_col_offset=13), Expr(value=Call(func=Name(id='spam', ctx=Load(), "
1021            "lineno=1, col_offset=0, end_lineno=1, end_col_offset=0), "
1022            "args=[Constant(value='eggs', lineno=1, col_offset=0, end_lineno=1, "
1023            "end_col_offset=0)], keywords=[], lineno=1, col_offset=0, end_lineno=1, "
1024            "end_col_offset=0), lineno=1, col_offset=0, end_lineno=1, end_col_offset=0)], "
1025            "type_ignores=[])"
1026        )
1027
1028    def test_increment_lineno(self):
1029        src = ast.parse('1 + 1', mode='eval')
1030        self.assertEqual(ast.increment_lineno(src, n=3), src)
1031        self.assertEqual(ast.dump(src, include_attributes=True),
1032            'Expression(body=BinOp(left=Constant(value=1, lineno=4, col_offset=0, '
1033            'end_lineno=4, end_col_offset=1), op=Add(), right=Constant(value=1, '
1034            'lineno=4, col_offset=4, end_lineno=4, end_col_offset=5), lineno=4, '
1035            'col_offset=0, end_lineno=4, end_col_offset=5))'
1036        )
1037        # issue10869: do not increment lineno of root twice
1038        src = ast.parse('1 + 1', mode='eval')
1039        self.assertEqual(ast.increment_lineno(src.body, n=3), src.body)
1040        self.assertEqual(ast.dump(src, include_attributes=True),
1041            'Expression(body=BinOp(left=Constant(value=1, lineno=4, col_offset=0, '
1042            'end_lineno=4, end_col_offset=1), op=Add(), right=Constant(value=1, '
1043            'lineno=4, col_offset=4, end_lineno=4, end_col_offset=5), lineno=4, '
1044            'col_offset=0, end_lineno=4, end_col_offset=5))'
1045        )
1046        src = ast.Call(
1047            func=ast.Name("test", ast.Load()), args=[], keywords=[], lineno=1
1048        )
1049        self.assertEqual(ast.increment_lineno(src).lineno, 2)
1050        self.assertIsNone(ast.increment_lineno(src).end_lineno)
1051
1052    def test_increment_lineno_on_module(self):
1053        src = ast.parse(dedent("""\
1054        a = 1
1055        b = 2 # type: ignore
1056        c = 3
1057        d = 4 # type: ignore@tag
1058        """), type_comments=True)
1059        ast.increment_lineno(src, n=5)
1060        self.assertEqual(src.type_ignores[0].lineno, 7)
1061        self.assertEqual(src.type_ignores[1].lineno, 9)
1062        self.assertEqual(src.type_ignores[1].tag, '@tag')
1063
1064    def test_iter_fields(self):
1065        node = ast.parse('foo()', mode='eval')
1066        d = dict(ast.iter_fields(node.body))
1067        self.assertEqual(d.pop('func').id, 'foo')
1068        self.assertEqual(d, {'keywords': [], 'args': []})
1069
1070    def test_iter_child_nodes(self):
1071        node = ast.parse("spam(23, 42, eggs='leek')", mode='eval')
1072        self.assertEqual(len(list(ast.iter_child_nodes(node.body))), 4)
1073        iterator = ast.iter_child_nodes(node.body)
1074        self.assertEqual(next(iterator).id, 'spam')
1075        self.assertEqual(next(iterator).value, 23)
1076        self.assertEqual(next(iterator).value, 42)
1077        self.assertEqual(ast.dump(next(iterator)),
1078            "keyword(arg='eggs', value=Constant(value='leek'))"
1079        )
1080
1081    def test_get_docstring(self):
1082        node = ast.parse('"""line one\n  line two"""')
1083        self.assertEqual(ast.get_docstring(node),
1084                         'line one\nline two')
1085
1086        node = ast.parse('class foo:\n  """line one\n  line two"""')
1087        self.assertEqual(ast.get_docstring(node.body[0]),
1088                         'line one\nline two')
1089
1090        node = ast.parse('def foo():\n  """line one\n  line two"""')
1091        self.assertEqual(ast.get_docstring(node.body[0]),
1092                         'line one\nline two')
1093
1094        node = ast.parse('async def foo():\n  """spam\n  ham"""')
1095        self.assertEqual(ast.get_docstring(node.body[0]), 'spam\nham')
1096
1097    def test_get_docstring_none(self):
1098        self.assertIsNone(ast.get_docstring(ast.parse('')))
1099        node = ast.parse('x = "not docstring"')
1100        self.assertIsNone(ast.get_docstring(node))
1101        node = ast.parse('def foo():\n  pass')
1102        self.assertIsNone(ast.get_docstring(node))
1103
1104        node = ast.parse('class foo:\n  pass')
1105        self.assertIsNone(ast.get_docstring(node.body[0]))
1106        node = ast.parse('class foo:\n  x = "not docstring"')
1107        self.assertIsNone(ast.get_docstring(node.body[0]))
1108        node = ast.parse('class foo:\n  def bar(self): pass')
1109        self.assertIsNone(ast.get_docstring(node.body[0]))
1110
1111        node = ast.parse('def foo():\n  pass')
1112        self.assertIsNone(ast.get_docstring(node.body[0]))
1113        node = ast.parse('def foo():\n  x = "not docstring"')
1114        self.assertIsNone(ast.get_docstring(node.body[0]))
1115
1116        node = ast.parse('async def foo():\n  pass')
1117        self.assertIsNone(ast.get_docstring(node.body[0]))
1118        node = ast.parse('async def foo():\n  x = "not docstring"')
1119        self.assertIsNone(ast.get_docstring(node.body[0]))
1120
1121    def test_multi_line_docstring_col_offset_and_lineno_issue16806(self):
1122        node = ast.parse(
1123            '"""line one\nline two"""\n\n'
1124            'def foo():\n  """line one\n  line two"""\n\n'
1125            '  def bar():\n    """line one\n    line two"""\n'
1126            '  """line one\n  line two"""\n'
1127            '"""line one\nline two"""\n\n'
1128        )
1129        self.assertEqual(node.body[0].col_offset, 0)
1130        self.assertEqual(node.body[0].lineno, 1)
1131        self.assertEqual(node.body[1].body[0].col_offset, 2)
1132        self.assertEqual(node.body[1].body[0].lineno, 5)
1133        self.assertEqual(node.body[1].body[1].body[0].col_offset, 4)
1134        self.assertEqual(node.body[1].body[1].body[0].lineno, 9)
1135        self.assertEqual(node.body[1].body[2].col_offset, 2)
1136        self.assertEqual(node.body[1].body[2].lineno, 11)
1137        self.assertEqual(node.body[2].col_offset, 0)
1138        self.assertEqual(node.body[2].lineno, 13)
1139
1140    def test_elif_stmt_start_position(self):
1141        node = ast.parse('if a:\n    pass\nelif b:\n    pass\n')
1142        elif_stmt = node.body[0].orelse[0]
1143        self.assertEqual(elif_stmt.lineno, 3)
1144        self.assertEqual(elif_stmt.col_offset, 0)
1145
1146    def test_elif_stmt_start_position_with_else(self):
1147        node = ast.parse('if a:\n    pass\nelif b:\n    pass\nelse:\n    pass\n')
1148        elif_stmt = node.body[0].orelse[0]
1149        self.assertEqual(elif_stmt.lineno, 3)
1150        self.assertEqual(elif_stmt.col_offset, 0)
1151
1152    def test_starred_expr_end_position_within_call(self):
1153        node = ast.parse('f(*[0, 1])')
1154        starred_expr = node.body[0].value.args[0]
1155        self.assertEqual(starred_expr.end_lineno, 1)
1156        self.assertEqual(starred_expr.end_col_offset, 9)
1157
1158    def test_literal_eval(self):
1159        self.assertEqual(ast.literal_eval('[1, 2, 3]'), [1, 2, 3])
1160        self.assertEqual(ast.literal_eval('{"foo": 42}'), {"foo": 42})
1161        self.assertEqual(ast.literal_eval('(True, False, None)'), (True, False, None))
1162        self.assertEqual(ast.literal_eval('{1, 2, 3}'), {1, 2, 3})
1163        self.assertEqual(ast.literal_eval('b"hi"'), b"hi")
1164        self.assertEqual(ast.literal_eval('set()'), set())
1165        self.assertRaises(ValueError, ast.literal_eval, 'foo()')
1166        self.assertEqual(ast.literal_eval('6'), 6)
1167        self.assertEqual(ast.literal_eval('+6'), 6)
1168        self.assertEqual(ast.literal_eval('-6'), -6)
1169        self.assertEqual(ast.literal_eval('3.25'), 3.25)
1170        self.assertEqual(ast.literal_eval('+3.25'), 3.25)
1171        self.assertEqual(ast.literal_eval('-3.25'), -3.25)
1172        self.assertEqual(repr(ast.literal_eval('-0.0')), '-0.0')
1173        self.assertRaises(ValueError, ast.literal_eval, '++6')
1174        self.assertRaises(ValueError, ast.literal_eval, '+True')
1175        self.assertRaises(ValueError, ast.literal_eval, '2+3')
1176
1177    def test_literal_eval_str_int_limit(self):
1178        with support.adjust_int_max_str_digits(4000):
1179            ast.literal_eval('3'*4000)  # no error
1180            with self.assertRaises(SyntaxError) as err_ctx:
1181                ast.literal_eval('3'*4001)
1182            self.assertIn('Exceeds the limit ', str(err_ctx.exception))
1183            self.assertIn(' Consider hexadecimal ', str(err_ctx.exception))
1184
1185    def test_literal_eval_complex(self):
1186        # Issue #4907
1187        self.assertEqual(ast.literal_eval('6j'), 6j)
1188        self.assertEqual(ast.literal_eval('-6j'), -6j)
1189        self.assertEqual(ast.literal_eval('6.75j'), 6.75j)
1190        self.assertEqual(ast.literal_eval('-6.75j'), -6.75j)
1191        self.assertEqual(ast.literal_eval('3+6j'), 3+6j)
1192        self.assertEqual(ast.literal_eval('-3+6j'), -3+6j)
1193        self.assertEqual(ast.literal_eval('3-6j'), 3-6j)
1194        self.assertEqual(ast.literal_eval('-3-6j'), -3-6j)
1195        self.assertEqual(ast.literal_eval('3.25+6.75j'), 3.25+6.75j)
1196        self.assertEqual(ast.literal_eval('-3.25+6.75j'), -3.25+6.75j)
1197        self.assertEqual(ast.literal_eval('3.25-6.75j'), 3.25-6.75j)
1198        self.assertEqual(ast.literal_eval('-3.25-6.75j'), -3.25-6.75j)
1199        self.assertEqual(ast.literal_eval('(3+6j)'), 3+6j)
1200        self.assertRaises(ValueError, ast.literal_eval, '-6j+3')
1201        self.assertRaises(ValueError, ast.literal_eval, '-6j+3j')
1202        self.assertRaises(ValueError, ast.literal_eval, '3+-6j')
1203        self.assertRaises(ValueError, ast.literal_eval, '3+(0+6j)')
1204        self.assertRaises(ValueError, ast.literal_eval, '-(3+6j)')
1205
1206    def test_literal_eval_malformed_dict_nodes(self):
1207        malformed = ast.Dict(keys=[ast.Constant(1), ast.Constant(2)], values=[ast.Constant(3)])
1208        self.assertRaises(ValueError, ast.literal_eval, malformed)
1209        malformed = ast.Dict(keys=[ast.Constant(1)], values=[ast.Constant(2), ast.Constant(3)])
1210        self.assertRaises(ValueError, ast.literal_eval, malformed)
1211
1212    def test_literal_eval_trailing_ws(self):
1213        self.assertEqual(ast.literal_eval("    -1"), -1)
1214        self.assertEqual(ast.literal_eval("\t\t-1"), -1)
1215        self.assertEqual(ast.literal_eval(" \t -1"), -1)
1216        self.assertRaises(IndentationError, ast.literal_eval, "\n -1")
1217
1218    def test_literal_eval_malformed_lineno(self):
1219        msg = r'malformed node or string on line 3:'
1220        with self.assertRaisesRegex(ValueError, msg):
1221            ast.literal_eval("{'a': 1,\n'b':2,\n'c':++3,\n'd':4}")
1222
1223        node = ast.UnaryOp(
1224            ast.UAdd(), ast.UnaryOp(ast.UAdd(), ast.Constant(6)))
1225        self.assertIsNone(getattr(node, 'lineno', None))
1226        msg = r'malformed node or string:'
1227        with self.assertRaisesRegex(ValueError, msg):
1228            ast.literal_eval(node)
1229
1230    def test_literal_eval_syntax_errors(self):
1231        with self.assertRaisesRegex(SyntaxError, "unexpected indent"):
1232            ast.literal_eval(r'''
1233                \
1234                (\
1235            \ ''')
1236
1237    def test_bad_integer(self):
1238        # issue13436: Bad error message with invalid numeric values
1239        body = [ast.ImportFrom(module='time',
1240                               names=[ast.alias(name='sleep')],
1241                               level=None,
1242                               lineno=None, col_offset=None)]
1243        mod = ast.Module(body, [])
1244        with self.assertRaises(ValueError) as cm:
1245            compile(mod, 'test', 'exec')
1246        self.assertIn("invalid integer value: None", str(cm.exception))
1247
1248    def test_level_as_none(self):
1249        body = [ast.ImportFrom(module='time',
1250                               names=[ast.alias(name='sleep',
1251                                                lineno=0, col_offset=0)],
1252                               level=None,
1253                               lineno=0, col_offset=0)]
1254        mod = ast.Module(body, [])
1255        code = compile(mod, 'test', 'exec')
1256        ns = {}
1257        exec(code, ns)
1258        self.assertIn('sleep', ns)
1259
1260    def test_recursion_direct(self):
1261        e = ast.UnaryOp(op=ast.Not(), lineno=0, col_offset=0)
1262        e.operand = e
1263        with self.assertRaises(RecursionError):
1264            with support.infinite_recursion():
1265                compile(ast.Expression(e), "<test>", "eval")
1266
1267    def test_recursion_indirect(self):
1268        e = ast.UnaryOp(op=ast.Not(), lineno=0, col_offset=0)
1269        f = ast.UnaryOp(op=ast.Not(), lineno=0, col_offset=0)
1270        e.operand = f
1271        f.operand = e
1272        with self.assertRaises(RecursionError):
1273            with support.infinite_recursion():
1274                compile(ast.Expression(e), "<test>", "eval")
1275
1276
1277class ASTValidatorTests(unittest.TestCase):
1278
1279    def mod(self, mod, msg=None, mode="exec", *, exc=ValueError):
1280        mod.lineno = mod.col_offset = 0
1281        ast.fix_missing_locations(mod)
1282        if msg is None:
1283            compile(mod, "<test>", mode)
1284        else:
1285            with self.assertRaises(exc) as cm:
1286                compile(mod, "<test>", mode)
1287            self.assertIn(msg, str(cm.exception))
1288
1289    def expr(self, node, msg=None, *, exc=ValueError):
1290        mod = ast.Module([ast.Expr(node)], [])
1291        self.mod(mod, msg, exc=exc)
1292
1293    def stmt(self, stmt, msg=None):
1294        mod = ast.Module([stmt], [])
1295        self.mod(mod, msg)
1296
1297    def test_module(self):
1298        m = ast.Interactive([ast.Expr(ast.Name("x", ast.Store()))])
1299        self.mod(m, "must have Load context", "single")
1300        m = ast.Expression(ast.Name("x", ast.Store()))
1301        self.mod(m, "must have Load context", "eval")
1302
1303    def _check_arguments(self, fac, check):
1304        def arguments(args=None, posonlyargs=None, vararg=None,
1305                      kwonlyargs=None, kwarg=None,
1306                      defaults=None, kw_defaults=None):
1307            if args is None:
1308                args = []
1309            if posonlyargs is None:
1310                posonlyargs = []
1311            if kwonlyargs is None:
1312                kwonlyargs = []
1313            if defaults is None:
1314                defaults = []
1315            if kw_defaults is None:
1316                kw_defaults = []
1317            args = ast.arguments(args, posonlyargs, vararg, kwonlyargs,
1318                                 kw_defaults, kwarg, defaults)
1319            return fac(args)
1320        args = [ast.arg("x", ast.Name("x", ast.Store()))]
1321        check(arguments(args=args), "must have Load context")
1322        check(arguments(posonlyargs=args), "must have Load context")
1323        check(arguments(kwonlyargs=args), "must have Load context")
1324        check(arguments(defaults=[ast.Num(3)]),
1325                       "more positional defaults than args")
1326        check(arguments(kw_defaults=[ast.Num(4)]),
1327                       "length of kwonlyargs is not the same as kw_defaults")
1328        args = [ast.arg("x", ast.Name("x", ast.Load()))]
1329        check(arguments(args=args, defaults=[ast.Name("x", ast.Store())]),
1330                       "must have Load context")
1331        args = [ast.arg("a", ast.Name("x", ast.Load())),
1332                ast.arg("b", ast.Name("y", ast.Load()))]
1333        check(arguments(kwonlyargs=args,
1334                          kw_defaults=[None, ast.Name("x", ast.Store())]),
1335                          "must have Load context")
1336
1337    def test_funcdef(self):
1338        a = ast.arguments([], [], None, [], [], None, [])
1339        f = ast.FunctionDef("x", a, [], [], None)
1340        self.stmt(f, "empty body on FunctionDef")
1341        f = ast.FunctionDef("x", a, [ast.Pass()], [ast.Name("x", ast.Store())],
1342                            None)
1343        self.stmt(f, "must have Load context")
1344        f = ast.FunctionDef("x", a, [ast.Pass()], [],
1345                            ast.Name("x", ast.Store()))
1346        self.stmt(f, "must have Load context")
1347        def fac(args):
1348            return ast.FunctionDef("x", args, [ast.Pass()], [], None)
1349        self._check_arguments(fac, self.stmt)
1350
1351    def test_classdef(self):
1352        def cls(bases=None, keywords=None, body=None, decorator_list=None):
1353            if bases is None:
1354                bases = []
1355            if keywords is None:
1356                keywords = []
1357            if body is None:
1358                body = [ast.Pass()]
1359            if decorator_list is None:
1360                decorator_list = []
1361            return ast.ClassDef("myclass", bases, keywords,
1362                                body, decorator_list)
1363        self.stmt(cls(bases=[ast.Name("x", ast.Store())]),
1364                  "must have Load context")
1365        self.stmt(cls(keywords=[ast.keyword("x", ast.Name("x", ast.Store()))]),
1366                  "must have Load context")
1367        self.stmt(cls(body=[]), "empty body on ClassDef")
1368        self.stmt(cls(body=[None]), "None disallowed")
1369        self.stmt(cls(decorator_list=[ast.Name("x", ast.Store())]),
1370                  "must have Load context")
1371
1372    def test_delete(self):
1373        self.stmt(ast.Delete([]), "empty targets on Delete")
1374        self.stmt(ast.Delete([None]), "None disallowed")
1375        self.stmt(ast.Delete([ast.Name("x", ast.Load())]),
1376                  "must have Del context")
1377
1378    def test_assign(self):
1379        self.stmt(ast.Assign([], ast.Num(3)), "empty targets on Assign")
1380        self.stmt(ast.Assign([None], ast.Num(3)), "None disallowed")
1381        self.stmt(ast.Assign([ast.Name("x", ast.Load())], ast.Num(3)),
1382                  "must have Store context")
1383        self.stmt(ast.Assign([ast.Name("x", ast.Store())],
1384                                ast.Name("y", ast.Store())),
1385                  "must have Load context")
1386
1387    def test_augassign(self):
1388        aug = ast.AugAssign(ast.Name("x", ast.Load()), ast.Add(),
1389                            ast.Name("y", ast.Load()))
1390        self.stmt(aug, "must have Store context")
1391        aug = ast.AugAssign(ast.Name("x", ast.Store()), ast.Add(),
1392                            ast.Name("y", ast.Store()))
1393        self.stmt(aug, "must have Load context")
1394
1395    def test_for(self):
1396        x = ast.Name("x", ast.Store())
1397        y = ast.Name("y", ast.Load())
1398        p = ast.Pass()
1399        self.stmt(ast.For(x, y, [], []), "empty body on For")
1400        self.stmt(ast.For(ast.Name("x", ast.Load()), y, [p], []),
1401                  "must have Store context")
1402        self.stmt(ast.For(x, ast.Name("y", ast.Store()), [p], []),
1403                  "must have Load context")
1404        e = ast.Expr(ast.Name("x", ast.Store()))
1405        self.stmt(ast.For(x, y, [e], []), "must have Load context")
1406        self.stmt(ast.For(x, y, [p], [e]), "must have Load context")
1407
1408    def test_while(self):
1409        self.stmt(ast.While(ast.Num(3), [], []), "empty body on While")
1410        self.stmt(ast.While(ast.Name("x", ast.Store()), [ast.Pass()], []),
1411                  "must have Load context")
1412        self.stmt(ast.While(ast.Num(3), [ast.Pass()],
1413                             [ast.Expr(ast.Name("x", ast.Store()))]),
1414                             "must have Load context")
1415
1416    def test_if(self):
1417        self.stmt(ast.If(ast.Num(3), [], []), "empty body on If")
1418        i = ast.If(ast.Name("x", ast.Store()), [ast.Pass()], [])
1419        self.stmt(i, "must have Load context")
1420        i = ast.If(ast.Num(3), [ast.Expr(ast.Name("x", ast.Store()))], [])
1421        self.stmt(i, "must have Load context")
1422        i = ast.If(ast.Num(3), [ast.Pass()],
1423                   [ast.Expr(ast.Name("x", ast.Store()))])
1424        self.stmt(i, "must have Load context")
1425
1426    def test_with(self):
1427        p = ast.Pass()
1428        self.stmt(ast.With([], [p]), "empty items on With")
1429        i = ast.withitem(ast.Num(3), None)
1430        self.stmt(ast.With([i], []), "empty body on With")
1431        i = ast.withitem(ast.Name("x", ast.Store()), None)
1432        self.stmt(ast.With([i], [p]), "must have Load context")
1433        i = ast.withitem(ast.Num(3), ast.Name("x", ast.Load()))
1434        self.stmt(ast.With([i], [p]), "must have Store context")
1435
1436    def test_raise(self):
1437        r = ast.Raise(None, ast.Num(3))
1438        self.stmt(r, "Raise with cause but no exception")
1439        r = ast.Raise(ast.Name("x", ast.Store()), None)
1440        self.stmt(r, "must have Load context")
1441        r = ast.Raise(ast.Num(4), ast.Name("x", ast.Store()))
1442        self.stmt(r, "must have Load context")
1443
1444    def test_try(self):
1445        p = ast.Pass()
1446        t = ast.Try([], [], [], [p])
1447        self.stmt(t, "empty body on Try")
1448        t = ast.Try([ast.Expr(ast.Name("x", ast.Store()))], [], [], [p])
1449        self.stmt(t, "must have Load context")
1450        t = ast.Try([p], [], [], [])
1451        self.stmt(t, "Try has neither except handlers nor finalbody")
1452        t = ast.Try([p], [], [p], [p])
1453        self.stmt(t, "Try has orelse but no except handlers")
1454        t = ast.Try([p], [ast.ExceptHandler(None, "x", [])], [], [])
1455        self.stmt(t, "empty body on ExceptHandler")
1456        e = [ast.ExceptHandler(ast.Name("x", ast.Store()), "y", [p])]
1457        self.stmt(ast.Try([p], e, [], []), "must have Load context")
1458        e = [ast.ExceptHandler(None, "x", [p])]
1459        t = ast.Try([p], e, [ast.Expr(ast.Name("x", ast.Store()))], [p])
1460        self.stmt(t, "must have Load context")
1461        t = ast.Try([p], e, [p], [ast.Expr(ast.Name("x", ast.Store()))])
1462        self.stmt(t, "must have Load context")
1463
1464    def test_try_star(self):
1465        p = ast.Pass()
1466        t = ast.TryStar([], [], [], [p])
1467        self.stmt(t, "empty body on TryStar")
1468        t = ast.TryStar([ast.Expr(ast.Name("x", ast.Store()))], [], [], [p])
1469        self.stmt(t, "must have Load context")
1470        t = ast.TryStar([p], [], [], [])
1471        self.stmt(t, "TryStar has neither except handlers nor finalbody")
1472        t = ast.TryStar([p], [], [p], [p])
1473        self.stmt(t, "TryStar has orelse but no except handlers")
1474        t = ast.TryStar([p], [ast.ExceptHandler(None, "x", [])], [], [])
1475        self.stmt(t, "empty body on ExceptHandler")
1476        e = [ast.ExceptHandler(ast.Name("x", ast.Store()), "y", [p])]
1477        self.stmt(ast.TryStar([p], e, [], []), "must have Load context")
1478        e = [ast.ExceptHandler(None, "x", [p])]
1479        t = ast.TryStar([p], e, [ast.Expr(ast.Name("x", ast.Store()))], [p])
1480        self.stmt(t, "must have Load context")
1481        t = ast.TryStar([p], e, [p], [ast.Expr(ast.Name("x", ast.Store()))])
1482        self.stmt(t, "must have Load context")
1483
1484    def test_assert(self):
1485        self.stmt(ast.Assert(ast.Name("x", ast.Store()), None),
1486                  "must have Load context")
1487        assrt = ast.Assert(ast.Name("x", ast.Load()),
1488                           ast.Name("y", ast.Store()))
1489        self.stmt(assrt, "must have Load context")
1490
1491    def test_import(self):
1492        self.stmt(ast.Import([]), "empty names on Import")
1493
1494    def test_importfrom(self):
1495        imp = ast.ImportFrom(None, [ast.alias("x", None)], -42)
1496        self.stmt(imp, "Negative ImportFrom level")
1497        self.stmt(ast.ImportFrom(None, [], 0), "empty names on ImportFrom")
1498
1499    def test_global(self):
1500        self.stmt(ast.Global([]), "empty names on Global")
1501
1502    def test_nonlocal(self):
1503        self.stmt(ast.Nonlocal([]), "empty names on Nonlocal")
1504
1505    def test_expr(self):
1506        e = ast.Expr(ast.Name("x", ast.Store()))
1507        self.stmt(e, "must have Load context")
1508
1509    def test_boolop(self):
1510        b = ast.BoolOp(ast.And(), [])
1511        self.expr(b, "less than 2 values")
1512        b = ast.BoolOp(ast.And(), [ast.Num(3)])
1513        self.expr(b, "less than 2 values")
1514        b = ast.BoolOp(ast.And(), [ast.Num(4), None])
1515        self.expr(b, "None disallowed")
1516        b = ast.BoolOp(ast.And(), [ast.Num(4), ast.Name("x", ast.Store())])
1517        self.expr(b, "must have Load context")
1518
1519    def test_unaryop(self):
1520        u = ast.UnaryOp(ast.Not(), ast.Name("x", ast.Store()))
1521        self.expr(u, "must have Load context")
1522
1523    def test_lambda(self):
1524        a = ast.arguments([], [], None, [], [], None, [])
1525        self.expr(ast.Lambda(a, ast.Name("x", ast.Store())),
1526                  "must have Load context")
1527        def fac(args):
1528            return ast.Lambda(args, ast.Name("x", ast.Load()))
1529        self._check_arguments(fac, self.expr)
1530
1531    def test_ifexp(self):
1532        l = ast.Name("x", ast.Load())
1533        s = ast.Name("y", ast.Store())
1534        for args in (s, l, l), (l, s, l), (l, l, s):
1535            self.expr(ast.IfExp(*args), "must have Load context")
1536
1537    def test_dict(self):
1538        d = ast.Dict([], [ast.Name("x", ast.Load())])
1539        self.expr(d, "same number of keys as values")
1540        d = ast.Dict([ast.Name("x", ast.Load())], [None])
1541        self.expr(d, "None disallowed")
1542
1543    def test_set(self):
1544        self.expr(ast.Set([None]), "None disallowed")
1545        s = ast.Set([ast.Name("x", ast.Store())])
1546        self.expr(s, "must have Load context")
1547
1548    def _check_comprehension(self, fac):
1549        self.expr(fac([]), "comprehension with no generators")
1550        g = ast.comprehension(ast.Name("x", ast.Load()),
1551                              ast.Name("x", ast.Load()), [], 0)
1552        self.expr(fac([g]), "must have Store context")
1553        g = ast.comprehension(ast.Name("x", ast.Store()),
1554                              ast.Name("x", ast.Store()), [], 0)
1555        self.expr(fac([g]), "must have Load context")
1556        x = ast.Name("x", ast.Store())
1557        y = ast.Name("y", ast.Load())
1558        g = ast.comprehension(x, y, [None], 0)
1559        self.expr(fac([g]), "None disallowed")
1560        g = ast.comprehension(x, y, [ast.Name("x", ast.Store())], 0)
1561        self.expr(fac([g]), "must have Load context")
1562
1563    def _simple_comp(self, fac):
1564        g = ast.comprehension(ast.Name("x", ast.Store()),
1565                              ast.Name("x", ast.Load()), [], 0)
1566        self.expr(fac(ast.Name("x", ast.Store()), [g]),
1567                  "must have Load context")
1568        def wrap(gens):
1569            return fac(ast.Name("x", ast.Store()), gens)
1570        self._check_comprehension(wrap)
1571
1572    def test_listcomp(self):
1573        self._simple_comp(ast.ListComp)
1574
1575    def test_setcomp(self):
1576        self._simple_comp(ast.SetComp)
1577
1578    def test_generatorexp(self):
1579        self._simple_comp(ast.GeneratorExp)
1580
1581    def test_dictcomp(self):
1582        g = ast.comprehension(ast.Name("y", ast.Store()),
1583                              ast.Name("p", ast.Load()), [], 0)
1584        c = ast.DictComp(ast.Name("x", ast.Store()),
1585                         ast.Name("y", ast.Load()), [g])
1586        self.expr(c, "must have Load context")
1587        c = ast.DictComp(ast.Name("x", ast.Load()),
1588                         ast.Name("y", ast.Store()), [g])
1589        self.expr(c, "must have Load context")
1590        def factory(comps):
1591            k = ast.Name("x", ast.Load())
1592            v = ast.Name("y", ast.Load())
1593            return ast.DictComp(k, v, comps)
1594        self._check_comprehension(factory)
1595
1596    def test_yield(self):
1597        self.expr(ast.Yield(ast.Name("x", ast.Store())), "must have Load")
1598        self.expr(ast.YieldFrom(ast.Name("x", ast.Store())), "must have Load")
1599
1600    def test_compare(self):
1601        left = ast.Name("x", ast.Load())
1602        comp = ast.Compare(left, [ast.In()], [])
1603        self.expr(comp, "no comparators")
1604        comp = ast.Compare(left, [ast.In()], [ast.Num(4), ast.Num(5)])
1605        self.expr(comp, "different number of comparators and operands")
1606        comp = ast.Compare(ast.Num("blah"), [ast.In()], [left])
1607        self.expr(comp)
1608        comp = ast.Compare(left, [ast.In()], [ast.Num("blah")])
1609        self.expr(comp)
1610
1611    def test_call(self):
1612        func = ast.Name("x", ast.Load())
1613        args = [ast.Name("y", ast.Load())]
1614        keywords = [ast.keyword("w", ast.Name("z", ast.Load()))]
1615        call = ast.Call(ast.Name("x", ast.Store()), args, keywords)
1616        self.expr(call, "must have Load context")
1617        call = ast.Call(func, [None], keywords)
1618        self.expr(call, "None disallowed")
1619        bad_keywords = [ast.keyword("w", ast.Name("z", ast.Store()))]
1620        call = ast.Call(func, args, bad_keywords)
1621        self.expr(call, "must have Load context")
1622
1623    def test_num(self):
1624        class subint(int):
1625            pass
1626        class subfloat(float):
1627            pass
1628        class subcomplex(complex):
1629            pass
1630        for obj in "0", "hello":
1631            self.expr(ast.Num(obj))
1632        for obj in subint(), subfloat(), subcomplex():
1633            self.expr(ast.Num(obj), "invalid type", exc=TypeError)
1634
1635    def test_attribute(self):
1636        attr = ast.Attribute(ast.Name("x", ast.Store()), "y", ast.Load())
1637        self.expr(attr, "must have Load context")
1638
1639    def test_subscript(self):
1640        sub = ast.Subscript(ast.Name("x", ast.Store()), ast.Num(3),
1641                            ast.Load())
1642        self.expr(sub, "must have Load context")
1643        x = ast.Name("x", ast.Load())
1644        sub = ast.Subscript(x, ast.Name("y", ast.Store()),
1645                            ast.Load())
1646        self.expr(sub, "must have Load context")
1647        s = ast.Name("x", ast.Store())
1648        for args in (s, None, None), (None, s, None), (None, None, s):
1649            sl = ast.Slice(*args)
1650            self.expr(ast.Subscript(x, sl, ast.Load()),
1651                      "must have Load context")
1652        sl = ast.Tuple([], ast.Load())
1653        self.expr(ast.Subscript(x, sl, ast.Load()))
1654        sl = ast.Tuple([s], ast.Load())
1655        self.expr(ast.Subscript(x, sl, ast.Load()), "must have Load context")
1656
1657    def test_starred(self):
1658        left = ast.List([ast.Starred(ast.Name("x", ast.Load()), ast.Store())],
1659                        ast.Store())
1660        assign = ast.Assign([left], ast.Num(4))
1661        self.stmt(assign, "must have Store context")
1662
1663    def _sequence(self, fac):
1664        self.expr(fac([None], ast.Load()), "None disallowed")
1665        self.expr(fac([ast.Name("x", ast.Store())], ast.Load()),
1666                  "must have Load context")
1667
1668    def test_list(self):
1669        self._sequence(ast.List)
1670
1671    def test_tuple(self):
1672        self._sequence(ast.Tuple)
1673
1674    def test_nameconstant(self):
1675        self.expr(ast.NameConstant(4))
1676
1677    def test_stdlib_validates(self):
1678        stdlib = os.path.dirname(ast.__file__)
1679        tests = [fn for fn in os.listdir(stdlib) if fn.endswith(".py")]
1680        tests.extend(["test/test_grammar.py", "test/test_unpack_ex.py"])
1681        for module in tests:
1682            with self.subTest(module):
1683                fn = os.path.join(stdlib, module)
1684                with open(fn, "r", encoding="utf-8") as fp:
1685                    source = fp.read()
1686                mod = ast.parse(source, fn)
1687                compile(mod, fn, "exec")
1688
1689    constant_1 = ast.Constant(1)
1690    pattern_1 = ast.MatchValue(constant_1)
1691
1692    constant_x = ast.Constant('x')
1693    pattern_x = ast.MatchValue(constant_x)
1694
1695    constant_true = ast.Constant(True)
1696    pattern_true = ast.MatchSingleton(True)
1697
1698    name_carter = ast.Name('carter', ast.Load())
1699
1700    _MATCH_PATTERNS = [
1701        ast.MatchValue(
1702            ast.Attribute(
1703                ast.Attribute(
1704                    ast.Name('x', ast.Store()),
1705                    'y', ast.Load()
1706                ),
1707                'z', ast.Load()
1708            )
1709        ),
1710        ast.MatchValue(
1711            ast.Attribute(
1712                ast.Attribute(
1713                    ast.Name('x', ast.Load()),
1714                    'y', ast.Store()
1715                ),
1716                'z', ast.Load()
1717            )
1718        ),
1719        ast.MatchValue(
1720            ast.Constant(...)
1721        ),
1722        ast.MatchValue(
1723            ast.Constant(True)
1724        ),
1725        ast.MatchValue(
1726            ast.Constant((1,2,3))
1727        ),
1728        ast.MatchSingleton('string'),
1729        ast.MatchSequence([
1730          ast.MatchSingleton('string')
1731        ]),
1732        ast.MatchSequence(
1733            [
1734                ast.MatchSequence(
1735                    [
1736                        ast.MatchSingleton('string')
1737                    ]
1738                )
1739            ]
1740        ),
1741        ast.MatchMapping(
1742            [constant_1, constant_true],
1743            [pattern_x]
1744        ),
1745        ast.MatchMapping(
1746            [constant_true, constant_1],
1747            [pattern_x, pattern_1],
1748            rest='True'
1749        ),
1750        ast.MatchMapping(
1751            [constant_true, ast.Starred(ast.Name('lol', ast.Load()), ast.Load())],
1752            [pattern_x, pattern_1],
1753            rest='legit'
1754        ),
1755        ast.MatchClass(
1756            ast.Attribute(
1757                ast.Attribute(
1758                    constant_x,
1759                    'y', ast.Load()),
1760                'z', ast.Load()),
1761            patterns=[], kwd_attrs=[], kwd_patterns=[]
1762        ),
1763        ast.MatchClass(
1764            name_carter,
1765            patterns=[],
1766            kwd_attrs=['True'],
1767            kwd_patterns=[pattern_1]
1768        ),
1769        ast.MatchClass(
1770            name_carter,
1771            patterns=[],
1772            kwd_attrs=[],
1773            kwd_patterns=[pattern_1]
1774        ),
1775        ast.MatchClass(
1776            name_carter,
1777            patterns=[ast.MatchSingleton('string')],
1778            kwd_attrs=[],
1779            kwd_patterns=[]
1780        ),
1781        ast.MatchClass(
1782            name_carter,
1783            patterns=[ast.MatchStar()],
1784            kwd_attrs=[],
1785            kwd_patterns=[]
1786        ),
1787        ast.MatchClass(
1788            name_carter,
1789            patterns=[],
1790            kwd_attrs=[],
1791            kwd_patterns=[ast.MatchStar()]
1792        ),
1793        ast.MatchClass(
1794            constant_true,  # invalid name
1795            patterns=[],
1796            kwd_attrs=['True'],
1797            kwd_patterns=[pattern_1]
1798        ),
1799        ast.MatchSequence(
1800            [
1801                ast.MatchStar("True")
1802            ]
1803        ),
1804        ast.MatchAs(
1805            name='False'
1806        ),
1807        ast.MatchOr(
1808            []
1809        ),
1810        ast.MatchOr(
1811            [pattern_1]
1812        ),
1813        ast.MatchOr(
1814            [pattern_1, pattern_x, ast.MatchSingleton('xxx')]
1815        ),
1816        ast.MatchAs(name="_"),
1817        ast.MatchStar(name="x"),
1818        ast.MatchSequence([ast.MatchStar("_")]),
1819        ast.MatchMapping([], [], rest="_"),
1820    ]
1821
1822    def test_match_validation_pattern(self):
1823        name_x = ast.Name('x', ast.Load())
1824        for pattern in self._MATCH_PATTERNS:
1825            with self.subTest(ast.dump(pattern, indent=4)):
1826                node = ast.Match(
1827                    subject=name_x,
1828                    cases = [
1829                        ast.match_case(
1830                            pattern=pattern,
1831                            body = [ast.Pass()]
1832                        )
1833                    ]
1834                )
1835                node = ast.fix_missing_locations(node)
1836                module = ast.Module([node], [])
1837                with self.assertRaises(ValueError):
1838                    compile(module, "<test>", "exec")
1839
1840
1841class ConstantTests(unittest.TestCase):
1842    """Tests on the ast.Constant node type."""
1843
1844    def compile_constant(self, value):
1845        tree = ast.parse("x = 123")
1846
1847        node = tree.body[0].value
1848        new_node = ast.Constant(value=value)
1849        ast.copy_location(new_node, node)
1850        tree.body[0].value = new_node
1851
1852        code = compile(tree, "<string>", "exec")
1853
1854        ns = {}
1855        exec(code, ns)
1856        return ns['x']
1857
1858    def test_validation(self):
1859        with self.assertRaises(TypeError) as cm:
1860            self.compile_constant([1, 2, 3])
1861        self.assertEqual(str(cm.exception),
1862                         "got an invalid type in Constant: list")
1863
1864    def test_singletons(self):
1865        for const in (None, False, True, Ellipsis, b'', frozenset()):
1866            with self.subTest(const=const):
1867                value = self.compile_constant(const)
1868                self.assertIs(value, const)
1869
1870    def test_values(self):
1871        nested_tuple = (1,)
1872        nested_frozenset = frozenset({1})
1873        for level in range(3):
1874            nested_tuple = (nested_tuple, 2)
1875            nested_frozenset = frozenset({nested_frozenset, 2})
1876        values = (123, 123.0, 123j,
1877                  "unicode", b'bytes',
1878                  tuple("tuple"), frozenset("frozenset"),
1879                  nested_tuple, nested_frozenset)
1880        for value in values:
1881            with self.subTest(value=value):
1882                result = self.compile_constant(value)
1883                self.assertEqual(result, value)
1884
1885    def test_assign_to_constant(self):
1886        tree = ast.parse("x = 1")
1887
1888        target = tree.body[0].targets[0]
1889        new_target = ast.Constant(value=1)
1890        ast.copy_location(new_target, target)
1891        tree.body[0].targets[0] = new_target
1892
1893        with self.assertRaises(ValueError) as cm:
1894            compile(tree, "string", "exec")
1895        self.assertEqual(str(cm.exception),
1896                         "expression which can't be assigned "
1897                         "to in Store context")
1898
1899    def test_get_docstring(self):
1900        tree = ast.parse("'docstring'\nx = 1")
1901        self.assertEqual(ast.get_docstring(tree), 'docstring')
1902
1903    def get_load_const(self, tree):
1904        # Compile to bytecode, disassemble and get parameter of LOAD_CONST
1905        # instructions
1906        co = compile(tree, '<string>', 'exec')
1907        consts = []
1908        for instr in dis.get_instructions(co):
1909            if instr.opname == 'LOAD_CONST':
1910                consts.append(instr.argval)
1911        return consts
1912
1913    @support.cpython_only
1914    def test_load_const(self):
1915        consts = [None,
1916                  True, False,
1917                  124,
1918                  2.0,
1919                  3j,
1920                  "unicode",
1921                  b'bytes',
1922                  (1, 2, 3)]
1923
1924        code = '\n'.join(['x={!r}'.format(const) for const in consts])
1925        code += '\nx = ...'
1926        consts.extend((Ellipsis, None))
1927
1928        tree = ast.parse(code)
1929        self.assertEqual(self.get_load_const(tree),
1930                         consts)
1931
1932        # Replace expression nodes with constants
1933        for assign, const in zip(tree.body, consts):
1934            assert isinstance(assign, ast.Assign), ast.dump(assign)
1935            new_node = ast.Constant(value=const)
1936            ast.copy_location(new_node, assign.value)
1937            assign.value = new_node
1938
1939        self.assertEqual(self.get_load_const(tree),
1940                         consts)
1941
1942    def test_literal_eval(self):
1943        tree = ast.parse("1 + 2")
1944        binop = tree.body[0].value
1945
1946        new_left = ast.Constant(value=10)
1947        ast.copy_location(new_left, binop.left)
1948        binop.left = new_left
1949
1950        new_right = ast.Constant(value=20j)
1951        ast.copy_location(new_right, binop.right)
1952        binop.right = new_right
1953
1954        self.assertEqual(ast.literal_eval(binop), 10+20j)
1955
1956    def test_string_kind(self):
1957        c = ast.parse('"x"', mode='eval').body
1958        self.assertEqual(c.value, "x")
1959        self.assertEqual(c.kind, None)
1960
1961        c = ast.parse('u"x"', mode='eval').body
1962        self.assertEqual(c.value, "x")
1963        self.assertEqual(c.kind, "u")
1964
1965        c = ast.parse('r"x"', mode='eval').body
1966        self.assertEqual(c.value, "x")
1967        self.assertEqual(c.kind, None)
1968
1969        c = ast.parse('b"x"', mode='eval').body
1970        self.assertEqual(c.value, b"x")
1971        self.assertEqual(c.kind, None)
1972
1973
1974class EndPositionTests(unittest.TestCase):
1975    """Tests for end position of AST nodes.
1976
1977    Testing end positions of nodes requires a bit of extra care
1978    because of how LL parsers work.
1979    """
1980    def _check_end_pos(self, ast_node, end_lineno, end_col_offset):
1981        self.assertEqual(ast_node.end_lineno, end_lineno)
1982        self.assertEqual(ast_node.end_col_offset, end_col_offset)
1983
1984    def _check_content(self, source, ast_node, content):
1985        self.assertEqual(ast.get_source_segment(source, ast_node), content)
1986
1987    def _parse_value(self, s):
1988        # Use duck-typing to support both single expression
1989        # and a right hand side of an assignment statement.
1990        return ast.parse(s).body[0].value
1991
1992    def test_lambda(self):
1993        s = 'lambda x, *y: None'
1994        lam = self._parse_value(s)
1995        self._check_content(s, lam.body, 'None')
1996        self._check_content(s, lam.args.args[0], 'x')
1997        self._check_content(s, lam.args.vararg, 'y')
1998
1999    def test_func_def(self):
2000        s = dedent('''
2001            def func(x: int,
2002                     *args: str,
2003                     z: float = 0,
2004                     **kwargs: Any) -> bool:
2005                return True
2006            ''').strip()
2007        fdef = ast.parse(s).body[0]
2008        self._check_end_pos(fdef, 5, 15)
2009        self._check_content(s, fdef.body[0], 'return True')
2010        self._check_content(s, fdef.args.args[0], 'x: int')
2011        self._check_content(s, fdef.args.args[0].annotation, 'int')
2012        self._check_content(s, fdef.args.kwarg, 'kwargs: Any')
2013        self._check_content(s, fdef.args.kwarg.annotation, 'Any')
2014
2015    def test_call(self):
2016        s = 'func(x, y=2, **kw)'
2017        call = self._parse_value(s)
2018        self._check_content(s, call.func, 'func')
2019        self._check_content(s, call.keywords[0].value, '2')
2020        self._check_content(s, call.keywords[1].value, 'kw')
2021
2022    def test_call_noargs(self):
2023        s = 'x[0]()'
2024        call = self._parse_value(s)
2025        self._check_content(s, call.func, 'x[0]')
2026        self._check_end_pos(call, 1, 6)
2027
2028    def test_class_def(self):
2029        s = dedent('''
2030            class C(A, B):
2031                x: int = 0
2032        ''').strip()
2033        cdef = ast.parse(s).body[0]
2034        self._check_end_pos(cdef, 2, 14)
2035        self._check_content(s, cdef.bases[1], 'B')
2036        self._check_content(s, cdef.body[0], 'x: int = 0')
2037
2038    def test_class_kw(self):
2039        s = 'class S(metaclass=abc.ABCMeta): pass'
2040        cdef = ast.parse(s).body[0]
2041        self._check_content(s, cdef.keywords[0].value, 'abc.ABCMeta')
2042
2043    def test_multi_line_str(self):
2044        s = dedent('''
2045            x = """Some multi-line text.
2046
2047            It goes on starting from same indent."""
2048        ''').strip()
2049        assign = ast.parse(s).body[0]
2050        self._check_end_pos(assign, 3, 40)
2051        self._check_end_pos(assign.value, 3, 40)
2052
2053    def test_continued_str(self):
2054        s = dedent('''
2055            x = "first part" \\
2056            "second part"
2057        ''').strip()
2058        assign = ast.parse(s).body[0]
2059        self._check_end_pos(assign, 2, 13)
2060        self._check_end_pos(assign.value, 2, 13)
2061
2062    def test_suites(self):
2063        # We intentionally put these into the same string to check
2064        # that empty lines are not part of the suite.
2065        s = dedent('''
2066            while True:
2067                pass
2068
2069            if one():
2070                x = None
2071            elif other():
2072                y = None
2073            else:
2074                z = None
2075
2076            for x, y in stuff:
2077                assert True
2078
2079            try:
2080                raise RuntimeError
2081            except TypeError as e:
2082                pass
2083
2084            pass
2085        ''').strip()
2086        mod = ast.parse(s)
2087        while_loop = mod.body[0]
2088        if_stmt = mod.body[1]
2089        for_loop = mod.body[2]
2090        try_stmt = mod.body[3]
2091        pass_stmt = mod.body[4]
2092
2093        self._check_end_pos(while_loop, 2, 8)
2094        self._check_end_pos(if_stmt, 9, 12)
2095        self._check_end_pos(for_loop, 12, 15)
2096        self._check_end_pos(try_stmt, 17, 8)
2097        self._check_end_pos(pass_stmt, 19, 4)
2098
2099        self._check_content(s, while_loop.test, 'True')
2100        self._check_content(s, if_stmt.body[0], 'x = None')
2101        self._check_content(s, if_stmt.orelse[0].test, 'other()')
2102        self._check_content(s, for_loop.target, 'x, y')
2103        self._check_content(s, try_stmt.body[0], 'raise RuntimeError')
2104        self._check_content(s, try_stmt.handlers[0].type, 'TypeError')
2105
2106    def test_fstring(self):
2107        s = 'x = f"abc {x + y} abc"'
2108        fstr = self._parse_value(s)
2109        binop = fstr.values[1].value
2110        self._check_content(s, binop, 'x + y')
2111
2112    def test_fstring_multi_line(self):
2113        s = dedent('''
2114            f"""Some multi-line text.
2115            {
2116            arg_one
2117            +
2118            arg_two
2119            }
2120            It goes on..."""
2121        ''').strip()
2122        fstr = self._parse_value(s)
2123        binop = fstr.values[1].value
2124        self._check_end_pos(binop, 5, 7)
2125        self._check_content(s, binop.left, 'arg_one')
2126        self._check_content(s, binop.right, 'arg_two')
2127
2128    def test_import_from_multi_line(self):
2129        s = dedent('''
2130            from x.y.z import (
2131                a, b, c as c
2132            )
2133        ''').strip()
2134        imp = ast.parse(s).body[0]
2135        self._check_end_pos(imp, 3, 1)
2136        self._check_end_pos(imp.names[2], 2, 16)
2137
2138    def test_slices(self):
2139        s1 = 'f()[1, 2] [0]'
2140        s2 = 'x[ a.b: c.d]'
2141        sm = dedent('''
2142            x[ a.b: f () ,
2143               g () : c.d
2144              ]
2145        ''').strip()
2146        i1, i2, im = map(self._parse_value, (s1, s2, sm))
2147        self._check_content(s1, i1.value, 'f()[1, 2]')
2148        self._check_content(s1, i1.value.slice, '1, 2')
2149        self._check_content(s2, i2.slice.lower, 'a.b')
2150        self._check_content(s2, i2.slice.upper, 'c.d')
2151        self._check_content(sm, im.slice.elts[0].upper, 'f ()')
2152        self._check_content(sm, im.slice.elts[1].lower, 'g ()')
2153        self._check_end_pos(im, 3, 3)
2154
2155    def test_binop(self):
2156        s = dedent('''
2157            (1 * 2 + (3 ) +
2158                 4
2159            )
2160        ''').strip()
2161        binop = self._parse_value(s)
2162        self._check_end_pos(binop, 2, 6)
2163        self._check_content(s, binop.right, '4')
2164        self._check_content(s, binop.left, '1 * 2 + (3 )')
2165        self._check_content(s, binop.left.right, '3')
2166
2167    def test_boolop(self):
2168        s = dedent('''
2169            if (one_condition and
2170                    (other_condition or yet_another_one)):
2171                pass
2172        ''').strip()
2173        bop = ast.parse(s).body[0].test
2174        self._check_end_pos(bop, 2, 44)
2175        self._check_content(s, bop.values[1],
2176                            'other_condition or yet_another_one')
2177
2178    def test_tuples(self):
2179        s1 = 'x = () ;'
2180        s2 = 'x = 1 , ;'
2181        s3 = 'x = (1 , 2 ) ;'
2182        sm = dedent('''
2183            x = (
2184                a, b,
2185            )
2186        ''').strip()
2187        t1, t2, t3, tm = map(self._parse_value, (s1, s2, s3, sm))
2188        self._check_content(s1, t1, '()')
2189        self._check_content(s2, t2, '1 ,')
2190        self._check_content(s3, t3, '(1 , 2 )')
2191        self._check_end_pos(tm, 3, 1)
2192
2193    def test_attribute_spaces(self):
2194        s = 'func(x. y .z)'
2195        call = self._parse_value(s)
2196        self._check_content(s, call, s)
2197        self._check_content(s, call.args[0], 'x. y .z')
2198
2199    def test_redundant_parenthesis(self):
2200        s = '( ( ( a + b ) ) )'
2201        v = ast.parse(s).body[0].value
2202        self.assertEqual(type(v).__name__, 'BinOp')
2203        self._check_content(s, v, 'a + b')
2204        s2 = 'await ' + s
2205        v = ast.parse(s2).body[0].value.value
2206        self.assertEqual(type(v).__name__, 'BinOp')
2207        self._check_content(s2, v, 'a + b')
2208
2209    def test_trailers_with_redundant_parenthesis(self):
2210        tests = (
2211            ('( ( ( a ) ) ) ( )', 'Call'),
2212            ('( ( ( a ) ) ) ( b )', 'Call'),
2213            ('( ( ( a ) ) ) [ b ]', 'Subscript'),
2214            ('( ( ( a ) ) ) . b', 'Attribute'),
2215        )
2216        for s, t in tests:
2217            with self.subTest(s):
2218                v = ast.parse(s).body[0].value
2219                self.assertEqual(type(v).__name__, t)
2220                self._check_content(s, v, s)
2221                s2 = 'await ' + s
2222                v = ast.parse(s2).body[0].value.value
2223                self.assertEqual(type(v).__name__, t)
2224                self._check_content(s2, v, s)
2225
2226    def test_displays(self):
2227        s1 = '[{}, {1, }, {1, 2,} ]'
2228        s2 = '{a: b, f (): g () ,}'
2229        c1 = self._parse_value(s1)
2230        c2 = self._parse_value(s2)
2231        self._check_content(s1, c1.elts[0], '{}')
2232        self._check_content(s1, c1.elts[1], '{1, }')
2233        self._check_content(s1, c1.elts[2], '{1, 2,}')
2234        self._check_content(s2, c2.keys[1], 'f ()')
2235        self._check_content(s2, c2.values[1], 'g ()')
2236
2237    def test_comprehensions(self):
2238        s = dedent('''
2239            x = [{x for x, y in stuff
2240                  if cond.x} for stuff in things]
2241        ''').strip()
2242        cmp = self._parse_value(s)
2243        self._check_end_pos(cmp, 2, 37)
2244        self._check_content(s, cmp.generators[0].iter, 'things')
2245        self._check_content(s, cmp.elt.generators[0].iter, 'stuff')
2246        self._check_content(s, cmp.elt.generators[0].ifs[0], 'cond.x')
2247        self._check_content(s, cmp.elt.generators[0].target, 'x, y')
2248
2249    def test_yield_await(self):
2250        s = dedent('''
2251            async def f():
2252                yield x
2253                await y
2254        ''').strip()
2255        fdef = ast.parse(s).body[0]
2256        self._check_content(s, fdef.body[0].value, 'yield x')
2257        self._check_content(s, fdef.body[1].value, 'await y')
2258
2259    def test_source_segment_multi(self):
2260        s_orig = dedent('''
2261            x = (
2262                a, b,
2263            ) + ()
2264        ''').strip()
2265        s_tuple = dedent('''
2266            (
2267                a, b,
2268            )
2269        ''').strip()
2270        binop = self._parse_value(s_orig)
2271        self.assertEqual(ast.get_source_segment(s_orig, binop.left), s_tuple)
2272
2273    def test_source_segment_padded(self):
2274        s_orig = dedent('''
2275            class C:
2276                def fun(self) -> None:
2277                    "ЖЖЖЖЖ"
2278        ''').strip()
2279        s_method = '    def fun(self) -> None:\n' \
2280                   '        "ЖЖЖЖЖ"'
2281        cdef = ast.parse(s_orig).body[0]
2282        self.assertEqual(ast.get_source_segment(s_orig, cdef.body[0], padded=True),
2283                         s_method)
2284
2285    def test_source_segment_endings(self):
2286        s = 'v = 1\r\nw = 1\nx = 1\n\ry = 1\rz = 1\r\n'
2287        v, w, x, y, z = ast.parse(s).body
2288        self._check_content(s, v, 'v = 1')
2289        self._check_content(s, w, 'w = 1')
2290        self._check_content(s, x, 'x = 1')
2291        self._check_content(s, y, 'y = 1')
2292        self._check_content(s, z, 'z = 1')
2293
2294    def test_source_segment_tabs(self):
2295        s = dedent('''
2296            class C:
2297              \t\f  def fun(self) -> None:
2298              \t\f      pass
2299        ''').strip()
2300        s_method = '  \t\f  def fun(self) -> None:\n' \
2301                   '  \t\f      pass'
2302
2303        cdef = ast.parse(s).body[0]
2304        self.assertEqual(ast.get_source_segment(s, cdef.body[0], padded=True), s_method)
2305
2306    def test_source_segment_missing_info(self):
2307        s = 'v = 1\r\nw = 1\nx = 1\n\ry = 1\r\n'
2308        v, w, x, y = ast.parse(s).body
2309        del v.lineno
2310        del w.end_lineno
2311        del x.col_offset
2312        del y.end_col_offset
2313        self.assertIsNone(ast.get_source_segment(s, v))
2314        self.assertIsNone(ast.get_source_segment(s, w))
2315        self.assertIsNone(ast.get_source_segment(s, x))
2316        self.assertIsNone(ast.get_source_segment(s, y))
2317
2318class NodeVisitorTests(unittest.TestCase):
2319    def test_old_constant_nodes(self):
2320        class Visitor(ast.NodeVisitor):
2321            def visit_Num(self, node):
2322                log.append((node.lineno, 'Num', node.n))
2323            def visit_Str(self, node):
2324                log.append((node.lineno, 'Str', node.s))
2325            def visit_Bytes(self, node):
2326                log.append((node.lineno, 'Bytes', node.s))
2327            def visit_NameConstant(self, node):
2328                log.append((node.lineno, 'NameConstant', node.value))
2329            def visit_Ellipsis(self, node):
2330                log.append((node.lineno, 'Ellipsis', ...))
2331        mod = ast.parse(dedent('''\
2332            i = 42
2333            f = 4.25
2334            c = 4.25j
2335            s = 'string'
2336            b = b'bytes'
2337            t = True
2338            n = None
2339            e = ...
2340            '''))
2341        visitor = Visitor()
2342        log = []
2343        with warnings.catch_warnings(record=True) as wlog:
2344            warnings.filterwarnings('always', '', DeprecationWarning)
2345            visitor.visit(mod)
2346        self.assertEqual(log, [
2347            (1, 'Num', 42),
2348            (2, 'Num', 4.25),
2349            (3, 'Num', 4.25j),
2350            (4, 'Str', 'string'),
2351            (5, 'Bytes', b'bytes'),
2352            (6, 'NameConstant', True),
2353            (7, 'NameConstant', None),
2354            (8, 'Ellipsis', ...),
2355        ])
2356        self.assertEqual([str(w.message) for w in wlog], [
2357            'visit_Num is deprecated; add visit_Constant',
2358            'visit_Num is deprecated; add visit_Constant',
2359            'visit_Num is deprecated; add visit_Constant',
2360            'visit_Str is deprecated; add visit_Constant',
2361            'visit_Bytes is deprecated; add visit_Constant',
2362            'visit_NameConstant is deprecated; add visit_Constant',
2363            'visit_NameConstant is deprecated; add visit_Constant',
2364            'visit_Ellipsis is deprecated; add visit_Constant',
2365        ])
2366
2367
2368@support.cpython_only
2369class ModuleStateTests(unittest.TestCase):
2370    # bpo-41194, bpo-41261, bpo-41631: The _ast module uses a global state.
2371
2372    def check_ast_module(self):
2373        # Check that the _ast module still works as expected
2374        code = 'x + 1'
2375        filename = '<string>'
2376        mode = 'eval'
2377
2378        # Create _ast.AST subclasses instances
2379        ast_tree = compile(code, filename, mode, flags=ast.PyCF_ONLY_AST)
2380
2381        # Call PyAST_Check()
2382        code = compile(ast_tree, filename, mode)
2383        self.assertIsInstance(code, types.CodeType)
2384
2385    def test_reload_module(self):
2386        # bpo-41194: Importing the _ast module twice must not crash.
2387        with support.swap_item(sys.modules, '_ast', None):
2388            del sys.modules['_ast']
2389            import _ast as ast1
2390
2391            del sys.modules['_ast']
2392            import _ast as ast2
2393
2394            self.check_ast_module()
2395
2396        # Unloading the two _ast module instances must not crash.
2397        del ast1
2398        del ast2
2399        support.gc_collect()
2400
2401        self.check_ast_module()
2402
2403    def test_sys_modules(self):
2404        # bpo-41631: Test reproducing a Mercurial crash when PyAST_Check()
2405        # imported the _ast module internally.
2406        lazy_mod = object()
2407
2408        def my_import(name, *args, **kw):
2409            sys.modules[name] = lazy_mod
2410            return lazy_mod
2411
2412        with support.swap_item(sys.modules, '_ast', None):
2413            del sys.modules['_ast']
2414
2415            with support.swap_attr(builtins, '__import__', my_import):
2416                # Test that compile() does not import the _ast module
2417                self.check_ast_module()
2418                self.assertNotIn('_ast', sys.modules)
2419
2420                # Sanity check of the test itself
2421                import _ast
2422                self.assertIs(_ast, lazy_mod)
2423
2424    def test_subinterpreter(self):
2425        # bpo-41631: Importing and using the _ast module in a subinterpreter
2426        # must not crash.
2427        code = dedent('''
2428            import _ast
2429            import ast
2430            import gc
2431            import sys
2432            import types
2433
2434            # Create _ast.AST subclasses instances and call PyAST_Check()
2435            ast_tree = compile('x+1', '<string>', 'eval',
2436                               flags=ast.PyCF_ONLY_AST)
2437            code = compile(ast_tree, 'string', 'eval')
2438            if not isinstance(code, types.CodeType):
2439                raise AssertionError
2440
2441            # Unloading the _ast module must not crash.
2442            del ast, _ast
2443            del sys.modules['ast'], sys.modules['_ast']
2444            gc.collect()
2445        ''')
2446        res = support.run_in_subinterp(code)
2447        self.assertEqual(res, 0)
2448
2449
2450def main():
2451    if __name__ != '__main__':
2452        return
2453    if sys.argv[1:] == ['-g']:
2454        for statements, kind in ((exec_tests, "exec"), (single_tests, "single"),
2455                                 (eval_tests, "eval")):
2456            print(kind+"_results = [")
2457            for statement in statements:
2458                tree = ast.parse(statement, "?", kind)
2459                print("%r," % (to_tuple(tree),))
2460            print("]")
2461        print("main()")
2462        raise SystemExit
2463    unittest.main()
2464
2465#### EVERYTHING BELOW IS GENERATED BY python Lib/test/test_ast.py -g  #####
2466exec_results = [
2467('Module', [('Expr', (1, 0, 1, 4), ('Constant', (1, 0, 1, 4), None, None))], []),
2468('Module', [('Expr', (1, 0, 1, 18), ('Constant', (1, 0, 1, 18), 'module docstring', None))], []),
2469('Module', [('FunctionDef', (1, 0, 1, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (1, 9, 1, 13))], [], None, None)], []),
2470('Module', [('FunctionDef', (1, 0, 1, 29), 'f', ('arguments', [], [], None, [], [], None, []), [('Expr', (1, 9, 1, 29), ('Constant', (1, 9, 1, 29), 'function docstring', None))], [], None, None)], []),
2471('Module', [('FunctionDef', (1, 0, 1, 14), 'f', ('arguments', [], [('arg', (1, 6, 1, 7), 'a', None, None)], None, [], [], None, []), [('Pass', (1, 10, 1, 14))], [], None, None)], []),
2472('Module', [('FunctionDef', (1, 0, 1, 16), 'f', ('arguments', [], [('arg', (1, 6, 1, 7), 'a', None, None)], None, [], [], None, [('Constant', (1, 8, 1, 9), 0, None)]), [('Pass', (1, 12, 1, 16))], [], None, None)], []),
2473('Module', [('FunctionDef', (1, 0, 1, 18), 'f', ('arguments', [], [], ('arg', (1, 7, 1, 11), 'args', None, None), [], [], None, []), [('Pass', (1, 14, 1, 18))], [], None, None)], []),
2474('Module', [('FunctionDef', (1, 0, 1, 23), 'f', ('arguments', [], [], ('arg', (1, 7, 1, 16), 'args', ('Starred', (1, 13, 1, 16), ('Name', (1, 14, 1, 16), 'Ts', ('Load',)), ('Load',)), None), [], [], None, []), [('Pass', (1, 19, 1, 23))], [], None, None)], []),
2475('Module', [('FunctionDef', (1, 0, 1, 36), 'f', ('arguments', [], [], ('arg', (1, 7, 1, 29), 'args', ('Starred', (1, 13, 1, 29), ('Subscript', (1, 14, 1, 29), ('Name', (1, 14, 1, 19), 'tuple', ('Load',)), ('Tuple', (1, 20, 1, 28), [('Name', (1, 20, 1, 23), 'int', ('Load',)), ('Constant', (1, 25, 1, 28), Ellipsis, None)], ('Load',)), ('Load',)), ('Load',)), None), [], [], None, []), [('Pass', (1, 32, 1, 36))], [], None, None)], []),
2476('Module', [('FunctionDef', (1, 0, 1, 36), 'f', ('arguments', [], [], ('arg', (1, 7, 1, 29), 'args', ('Starred', (1, 13, 1, 29), ('Subscript', (1, 14, 1, 29), ('Name', (1, 14, 1, 19), 'tuple', ('Load',)), ('Tuple', (1, 20, 1, 28), [('Name', (1, 20, 1, 23), 'int', ('Load',)), ('Starred', (1, 25, 1, 28), ('Name', (1, 26, 1, 28), 'Ts', ('Load',)), ('Load',))], ('Load',)), ('Load',)), ('Load',)), None), [], [], None, []), [('Pass', (1, 32, 1, 36))], [], None, None)], []),
2477('Module', [('FunctionDef', (1, 0, 1, 21), 'f', ('arguments', [], [], None, [], [], ('arg', (1, 8, 1, 14), 'kwargs', None, None), []), [('Pass', (1, 17, 1, 21))], [], None, None)], []),
2478('Module', [('FunctionDef', (1, 0, 1, 71), 'f', ('arguments', [], [('arg', (1, 6, 1, 7), 'a', None, None), ('arg', (1, 9, 1, 10), 'b', None, None), ('arg', (1, 14, 1, 15), 'c', None, None), ('arg', (1, 22, 1, 23), 'd', None, None), ('arg', (1, 28, 1, 29), 'e', None, None)], ('arg', (1, 35, 1, 39), 'args', None, None), [('arg', (1, 41, 1, 42), 'f', None, None)], [('Constant', (1, 43, 1, 45), 42, None)], ('arg', (1, 49, 1, 55), 'kwargs', None, None), [('Constant', (1, 11, 1, 12), 1, None), ('Constant', (1, 16, 1, 20), None, None), ('List', (1, 24, 1, 26), [], ('Load',)), ('Dict', (1, 30, 1, 32), [], [])]), [('Expr', (1, 58, 1, 71), ('Constant', (1, 58, 1, 71), 'doc for f()', None))], [], None, None)], []),
2479('Module', [('FunctionDef', (1, 0, 1, 27), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (1, 23, 1, 27))], [], ('Subscript', (1, 11, 1, 21), ('Name', (1, 11, 1, 16), 'tuple', ('Load',)), ('Tuple', (1, 17, 1, 20), [('Starred', (1, 17, 1, 20), ('Name', (1, 18, 1, 20), 'Ts', ('Load',)), ('Load',))], ('Load',)), ('Load',)), None)], []),
2480('Module', [('FunctionDef', (1, 0, 1, 32), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (1, 28, 1, 32))], [], ('Subscript', (1, 11, 1, 26), ('Name', (1, 11, 1, 16), 'tuple', ('Load',)), ('Tuple', (1, 17, 1, 25), [('Name', (1, 17, 1, 20), 'int', ('Load',)), ('Starred', (1, 22, 1, 25), ('Name', (1, 23, 1, 25), 'Ts', ('Load',)), ('Load',))], ('Load',)), ('Load',)), None)], []),
2481('Module', [('FunctionDef', (1, 0, 1, 45), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (1, 41, 1, 45))], [], ('Subscript', (1, 11, 1, 39), ('Name', (1, 11, 1, 16), 'tuple', ('Load',)), ('Tuple', (1, 17, 1, 38), [('Name', (1, 17, 1, 20), 'int', ('Load',)), ('Starred', (1, 22, 1, 38), ('Subscript', (1, 23, 1, 38), ('Name', (1, 23, 1, 28), 'tuple', ('Load',)), ('Tuple', (1, 29, 1, 37), [('Name', (1, 29, 1, 32), 'int', ('Load',)), ('Constant', (1, 34, 1, 37), Ellipsis, None)], ('Load',)), ('Load',)), ('Load',))], ('Load',)), ('Load',)), None)], []),
2482('Module', [('ClassDef', (1, 0, 1, 12), 'C', [], [], [('Pass', (1, 8, 1, 12))], [])], []),
2483('Module', [('ClassDef', (1, 0, 1, 32), 'C', [], [], [('Expr', (1, 9, 1, 32), ('Constant', (1, 9, 1, 32), 'docstring for class C', None))], [])], []),
2484('Module', [('ClassDef', (1, 0, 1, 21), 'C', [('Name', (1, 8, 1, 14), 'object', ('Load',))], [], [('Pass', (1, 17, 1, 21))], [])], []),
2485('Module', [('FunctionDef', (1, 0, 1, 16), 'f', ('arguments', [], [], None, [], [], None, []), [('Return', (1, 8, 1, 16), ('Constant', (1, 15, 1, 16), 1, None))], [], None, None)], []),
2486('Module', [('Delete', (1, 0, 1, 5), [('Name', (1, 4, 1, 5), 'v', ('Del',))])], []),
2487('Module', [('Assign', (1, 0, 1, 5), [('Name', (1, 0, 1, 1), 'v', ('Store',))], ('Constant', (1, 4, 1, 5), 1, None), None)], []),
2488('Module', [('Assign', (1, 0, 1, 7), [('Tuple', (1, 0, 1, 3), [('Name', (1, 0, 1, 1), 'a', ('Store',)), ('Name', (1, 2, 1, 3), 'b', ('Store',))], ('Store',))], ('Name', (1, 6, 1, 7), 'c', ('Load',)), None)], []),
2489('Module', [('Assign', (1, 0, 1, 9), [('Tuple', (1, 0, 1, 5), [('Name', (1, 1, 1, 2), 'a', ('Store',)), ('Name', (1, 3, 1, 4), 'b', ('Store',))], ('Store',))], ('Name', (1, 8, 1, 9), 'c', ('Load',)), None)], []),
2490('Module', [('Assign', (1, 0, 1, 9), [('List', (1, 0, 1, 5), [('Name', (1, 1, 1, 2), 'a', ('Store',)), ('Name', (1, 3, 1, 4), 'b', ('Store',))], ('Store',))], ('Name', (1, 8, 1, 9), 'c', ('Load',)), None)], []),
2491('Module', [('AnnAssign', (1, 0, 1, 13), ('Name', (1, 0, 1, 1), 'x', ('Store',)), ('Subscript', (1, 3, 1, 13), ('Name', (1, 3, 1, 8), 'tuple', ('Load',)), ('Tuple', (1, 9, 1, 12), [('Starred', (1, 9, 1, 12), ('Name', (1, 10, 1, 12), 'Ts', ('Load',)), ('Load',))], ('Load',)), ('Load',)), None, 1)], []),
2492('Module', [('AnnAssign', (1, 0, 1, 18), ('Name', (1, 0, 1, 1), 'x', ('Store',)), ('Subscript', (1, 3, 1, 18), ('Name', (1, 3, 1, 8), 'tuple', ('Load',)), ('Tuple', (1, 9, 1, 17), [('Name', (1, 9, 1, 12), 'int', ('Load',)), ('Starred', (1, 14, 1, 17), ('Name', (1, 15, 1, 17), 'Ts', ('Load',)), ('Load',))], ('Load',)), ('Load',)), None, 1)], []),
2493('Module', [('AnnAssign', (1, 0, 1, 31), ('Name', (1, 0, 1, 1), 'x', ('Store',)), ('Subscript', (1, 3, 1, 31), ('Name', (1, 3, 1, 8), 'tuple', ('Load',)), ('Tuple', (1, 9, 1, 30), [('Name', (1, 9, 1, 12), 'int', ('Load',)), ('Starred', (1, 14, 1, 30), ('Subscript', (1, 15, 1, 30), ('Name', (1, 15, 1, 20), 'tuple', ('Load',)), ('Tuple', (1, 21, 1, 29), [('Name', (1, 21, 1, 24), 'str', ('Load',)), ('Constant', (1, 26, 1, 29), Ellipsis, None)], ('Load',)), ('Load',)), ('Load',))], ('Load',)), ('Load',)), None, 1)], []),
2494('Module', [('AugAssign', (1, 0, 1, 6), ('Name', (1, 0, 1, 1), 'v', ('Store',)), ('Add',), ('Constant', (1, 5, 1, 6), 1, None))], []),
2495('Module', [('For', (1, 0, 1, 15), ('Name', (1, 4, 1, 5), 'v', ('Store',)), ('Name', (1, 9, 1, 10), 'v', ('Load',)), [('Pass', (1, 11, 1, 15))], [], None)], []),
2496('Module', [('While', (1, 0, 1, 12), ('Name', (1, 6, 1, 7), 'v', ('Load',)), [('Pass', (1, 8, 1, 12))], [])], []),
2497('Module', [('If', (1, 0, 1, 9), ('Name', (1, 3, 1, 4), 'v', ('Load',)), [('Pass', (1, 5, 1, 9))], [])], []),
2498('Module', [('If', (1, 0, 4, 6), ('Name', (1, 3, 1, 4), 'a', ('Load',)), [('Pass', (2, 2, 2, 6))], [('If', (3, 0, 4, 6), ('Name', (3, 5, 3, 6), 'b', ('Load',)), [('Pass', (4, 2, 4, 6))], [])])], []),
2499('Module', [('If', (1, 0, 6, 6), ('Name', (1, 3, 1, 4), 'a', ('Load',)), [('Pass', (2, 2, 2, 6))], [('If', (3, 0, 6, 6), ('Name', (3, 5, 3, 6), 'b', ('Load',)), [('Pass', (4, 2, 4, 6))], [('Pass', (6, 2, 6, 6))])])], []),
2500('Module', [('With', (1, 0, 1, 17), [('withitem', ('Name', (1, 5, 1, 6), 'x', ('Load',)), ('Name', (1, 10, 1, 11), 'y', ('Store',)))], [('Pass', (1, 13, 1, 17))], None)], []),
2501('Module', [('With', (1, 0, 1, 25), [('withitem', ('Name', (1, 5, 1, 6), 'x', ('Load',)), ('Name', (1, 10, 1, 11), 'y', ('Store',))), ('withitem', ('Name', (1, 13, 1, 14), 'z', ('Load',)), ('Name', (1, 18, 1, 19), 'q', ('Store',)))], [('Pass', (1, 21, 1, 25))], None)], []),
2502('Module', [('Raise', (1, 0, 1, 25), ('Call', (1, 6, 1, 25), ('Name', (1, 6, 1, 15), 'Exception', ('Load',)), [('Constant', (1, 16, 1, 24), 'string', None)], []), None)], []),
2503('Module', [('Try', (1, 0, 4, 6), [('Pass', (2, 2, 2, 6))], [('ExceptHandler', (3, 0, 4, 6), ('Name', (3, 7, 3, 16), 'Exception', ('Load',)), None, [('Pass', (4, 2, 4, 6))])], [], [])], []),
2504('Module', [('Try', (1, 0, 4, 6), [('Pass', (2, 2, 2, 6))], [], [], [('Pass', (4, 2, 4, 6))])], []),
2505('Module', [('TryStar', (1, 0, 4, 6), [('Pass', (2, 2, 2, 6))], [('ExceptHandler', (3, 0, 4, 6), ('Name', (3, 8, 3, 17), 'Exception', ('Load',)), None, [('Pass', (4, 2, 4, 6))])], [], [])], []),
2506('Module', [('Assert', (1, 0, 1, 8), ('Name', (1, 7, 1, 8), 'v', ('Load',)), None)], []),
2507('Module', [('Import', (1, 0, 1, 10), [('alias', (1, 7, 1, 10), 'sys', None)])], []),
2508('Module', [('ImportFrom', (1, 0, 1, 17), 'sys', [('alias', (1, 16, 1, 17), 'v', None)], 0)], []),
2509('Module', [('Global', (1, 0, 1, 8), ['v'])], []),
2510('Module', [('Expr', (1, 0, 1, 1), ('Constant', (1, 0, 1, 1), 1, None))], []),
2511('Module', [('Pass', (1, 0, 1, 4))], []),
2512('Module', [('For', (1, 0, 1, 16), ('Name', (1, 4, 1, 5), 'v', ('Store',)), ('Name', (1, 9, 1, 10), 'v', ('Load',)), [('Break', (1, 11, 1, 16))], [], None)], []),
2513('Module', [('For', (1, 0, 1, 19), ('Name', (1, 4, 1, 5), 'v', ('Store',)), ('Name', (1, 9, 1, 10), 'v', ('Load',)), [('Continue', (1, 11, 1, 19))], [], None)], []),
2514('Module', [('For', (1, 0, 1, 18), ('Tuple', (1, 4, 1, 7), [('Name', (1, 4, 1, 5), 'a', ('Store',)), ('Name', (1, 6, 1, 7), 'b', ('Store',))], ('Store',)), ('Name', (1, 11, 1, 12), 'c', ('Load',)), [('Pass', (1, 14, 1, 18))], [], None)], []),
2515('Module', [('For', (1, 0, 1, 20), ('Tuple', (1, 4, 1, 9), [('Name', (1, 5, 1, 6), 'a', ('Store',)), ('Name', (1, 7, 1, 8), 'b', ('Store',))], ('Store',)), ('Name', (1, 13, 1, 14), 'c', ('Load',)), [('Pass', (1, 16, 1, 20))], [], None)], []),
2516('Module', [('For', (1, 0, 1, 20), ('List', (1, 4, 1, 9), [('Name', (1, 5, 1, 6), 'a', ('Store',)), ('Name', (1, 7, 1, 8), 'b', ('Store',))], ('Store',)), ('Name', (1, 13, 1, 14), 'c', ('Load',)), [('Pass', (1, 16, 1, 20))], [], None)], []),
2517('Module', [('Expr', (1, 0, 11, 5), ('GeneratorExp', (1, 0, 11, 5), ('Tuple', (2, 4, 6, 5), [('Name', (3, 4, 3, 6), 'Aa', ('Load',)), ('Name', (5, 7, 5, 9), 'Bb', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (8, 4, 10, 6), [('Name', (8, 4, 8, 6), 'Aa', ('Store',)), ('Name', (10, 4, 10, 6), 'Bb', ('Store',))], ('Store',)), ('Name', (10, 10, 10, 12), 'Cc', ('Load',)), [], 0)]))], []),
2518('Module', [('Expr', (1, 0, 1, 34), ('DictComp', (1, 0, 1, 34), ('Name', (1, 1, 1, 2), 'a', ('Load',)), ('Name', (1, 5, 1, 6), 'b', ('Load',)), [('comprehension', ('Name', (1, 11, 1, 12), 'w', ('Store',)), ('Name', (1, 16, 1, 17), 'x', ('Load',)), [], 0), ('comprehension', ('Name', (1, 22, 1, 23), 'm', ('Store',)), ('Name', (1, 27, 1, 28), 'p', ('Load',)), [('Name', (1, 32, 1, 33), 'g', ('Load',))], 0)]))], []),
2519('Module', [('Expr', (1, 0, 1, 20), ('DictComp', (1, 0, 1, 20), ('Name', (1, 1, 1, 2), 'a', ('Load',)), ('Name', (1, 5, 1, 6), 'b', ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'v', ('Store',)), ('Name', (1, 13, 1, 14), 'w', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'x', ('Load',)), [], 0)]))], []),
2520('Module', [('Expr', (1, 0, 1, 19), ('SetComp', (1, 0, 1, 19), ('Name', (1, 1, 1, 2), 'r', ('Load',)), [('comprehension', ('Name', (1, 7, 1, 8), 'l', ('Store',)), ('Name', (1, 12, 1, 13), 'x', ('Load',)), [('Name', (1, 17, 1, 18), 'g', ('Load',))], 0)]))], []),
2521('Module', [('Expr', (1, 0, 1, 16), ('SetComp', (1, 0, 1, 16), ('Name', (1, 1, 1, 2), 'r', ('Load',)), [('comprehension', ('Tuple', (1, 7, 1, 10), [('Name', (1, 7, 1, 8), 'l', ('Store',)), ('Name', (1, 9, 1, 10), 'm', ('Store',))], ('Store',)), ('Name', (1, 14, 1, 15), 'x', ('Load',)), [], 0)]))], []),
2522('Module', [('AsyncFunctionDef', (1, 0, 3, 18), 'f', ('arguments', [], [], None, [], [], None, []), [('Expr', (2, 1, 2, 17), ('Constant', (2, 1, 2, 17), 'async function', None)), ('Expr', (3, 1, 3, 18), ('Await', (3, 1, 3, 18), ('Call', (3, 7, 3, 18), ('Name', (3, 7, 3, 16), 'something', ('Load',)), [], [])))], [], None, None)], []),
2523('Module', [('AsyncFunctionDef', (1, 0, 3, 8), 'f', ('arguments', [], [], None, [], [], None, []), [('AsyncFor', (2, 1, 3, 8), ('Name', (2, 11, 2, 12), 'e', ('Store',)), ('Name', (2, 16, 2, 17), 'i', ('Load',)), [('Expr', (2, 19, 2, 20), ('Constant', (2, 19, 2, 20), 1, None))], [('Expr', (3, 7, 3, 8), ('Constant', (3, 7, 3, 8), 2, None))], None)], [], None, None)], []),
2524('Module', [('AsyncFunctionDef', (1, 0, 2, 21), 'f', ('arguments', [], [], None, [], [], None, []), [('AsyncWith', (2, 1, 2, 21), [('withitem', ('Name', (2, 12, 2, 13), 'a', ('Load',)), ('Name', (2, 17, 2, 18), 'b', ('Store',)))], [('Expr', (2, 20, 2, 21), ('Constant', (2, 20, 2, 21), 1, None))], None)], [], None, None)], []),
2525('Module', [('Expr', (1, 0, 1, 14), ('Dict', (1, 0, 1, 14), [None, ('Constant', (1, 10, 1, 11), 2, None)], [('Dict', (1, 3, 1, 8), [('Constant', (1, 4, 1, 5), 1, None)], [('Constant', (1, 6, 1, 7), 2, None)]), ('Constant', (1, 12, 1, 13), 3, None)]))], []),
2526('Module', [('Expr', (1, 0, 1, 12), ('Set', (1, 0, 1, 12), [('Starred', (1, 1, 1, 8), ('Set', (1, 2, 1, 8), [('Constant', (1, 3, 1, 4), 1, None), ('Constant', (1, 6, 1, 7), 2, None)]), ('Load',)), ('Constant', (1, 10, 1, 11), 3, None)]))], []),
2527('Module', [('AsyncFunctionDef', (1, 0, 2, 21), 'f', ('arguments', [], [], None, [], [], None, []), [('Expr', (2, 1, 2, 21), ('ListComp', (2, 1, 2, 21), ('Name', (2, 2, 2, 3), 'i', ('Load',)), [('comprehension', ('Name', (2, 14, 2, 15), 'b', ('Store',)), ('Name', (2, 19, 2, 20), 'c', ('Load',)), [], 1)]))], [], None, None)], []),
2528('Module', [('FunctionDef', (4, 0, 4, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (4, 9, 4, 13))], [('Name', (1, 1, 1, 6), 'deco1', ('Load',)), ('Call', (2, 1, 2, 8), ('Name', (2, 1, 2, 6), 'deco2', ('Load',)), [], []), ('Call', (3, 1, 3, 9), ('Name', (3, 1, 3, 6), 'deco3', ('Load',)), [('Constant', (3, 7, 3, 8), 1, None)], [])], None, None)], []),
2529('Module', [('AsyncFunctionDef', (4, 0, 4, 19), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (4, 15, 4, 19))], [('Name', (1, 1, 1, 6), 'deco1', ('Load',)), ('Call', (2, 1, 2, 8), ('Name', (2, 1, 2, 6), 'deco2', ('Load',)), [], []), ('Call', (3, 1, 3, 9), ('Name', (3, 1, 3, 6), 'deco3', ('Load',)), [('Constant', (3, 7, 3, 8), 1, None)], [])], None, None)], []),
2530('Module', [('ClassDef', (4, 0, 4, 13), 'C', [], [], [('Pass', (4, 9, 4, 13))], [('Name', (1, 1, 1, 6), 'deco1', ('Load',)), ('Call', (2, 1, 2, 8), ('Name', (2, 1, 2, 6), 'deco2', ('Load',)), [], []), ('Call', (3, 1, 3, 9), ('Name', (3, 1, 3, 6), 'deco3', ('Load',)), [('Constant', (3, 7, 3, 8), 1, None)], [])])], []),
2531('Module', [('FunctionDef', (2, 0, 2, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (2, 9, 2, 13))], [('Call', (1, 1, 1, 19), ('Name', (1, 1, 1, 5), 'deco', ('Load',)), [('GeneratorExp', (1, 5, 1, 19), ('Name', (1, 6, 1, 7), 'a', ('Load',)), [('comprehension', ('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 17, 1, 18), 'b', ('Load',)), [], 0)])], [])], None, None)], []),
2532('Module', [('FunctionDef', (2, 0, 2, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (2, 9, 2, 13))], [('Attribute', (1, 1, 1, 6), ('Attribute', (1, 1, 1, 4), ('Name', (1, 1, 1, 2), 'a', ('Load',)), 'b', ('Load',)), 'c', ('Load',))], None, None)], []),
2533('Module', [('Expr', (1, 0, 1, 8), ('NamedExpr', (1, 1, 1, 7), ('Name', (1, 1, 1, 2), 'a', ('Store',)), ('Constant', (1, 6, 1, 7), 1, None)))], []),
2534('Module', [('FunctionDef', (1, 0, 1, 18), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [], None, [], [], None, []), [('Pass', (1, 14, 1, 18))], [], None, None)], []),
2535('Module', [('FunctionDef', (1, 0, 1, 26), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 12, 1, 13), 'c', None, None), ('arg', (1, 15, 1, 16), 'd', None, None), ('arg', (1, 18, 1, 19), 'e', None, None)], None, [], [], None, []), [('Pass', (1, 22, 1, 26))], [], None, None)], []),
2536('Module', [('FunctionDef', (1, 0, 1, 29), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 12, 1, 13), 'c', None, None)], None, [('arg', (1, 18, 1, 19), 'd', None, None), ('arg', (1, 21, 1, 22), 'e', None, None)], [None, None], None, []), [('Pass', (1, 25, 1, 29))], [], None, None)], []),
2537('Module', [('FunctionDef', (1, 0, 1, 39), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 12, 1, 13), 'c', None, None)], None, [('arg', (1, 18, 1, 19), 'd', None, None), ('arg', (1, 21, 1, 22), 'e', None, None)], [None, None], ('arg', (1, 26, 1, 32), 'kwargs', None, None), []), [('Pass', (1, 35, 1, 39))], [], None, None)], []),
2538('Module', [('FunctionDef', (1, 0, 1, 20), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [], None, [], [], None, [('Constant', (1, 8, 1, 9), 1, None)]), [('Pass', (1, 16, 1, 20))], [], None, None)], []),
2539('Module', [('FunctionDef', (1, 0, 1, 29), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None), ('arg', (1, 19, 1, 20), 'c', None, None)], None, [], [], None, [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None), ('Constant', (1, 21, 1, 22), 4, None)]), [('Pass', (1, 25, 1, 29))], [], None, None)], []),
2540('Module', [('FunctionDef', (1, 0, 1, 32), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [('Constant', (1, 24, 1, 25), 4, None)], None, [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 28, 1, 32))], [], None, None)], []),
2541('Module', [('FunctionDef', (1, 0, 1, 30), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [None], None, [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 26, 1, 30))], [], None, None)], []),
2542('Module', [('FunctionDef', (1, 0, 1, 42), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [('Constant', (1, 24, 1, 25), 4, None)], ('arg', (1, 29, 1, 35), 'kwargs', None, None), [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 38, 1, 42))], [], None, None)], []),
2543('Module', [('FunctionDef', (1, 0, 1, 40), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [None], ('arg', (1, 27, 1, 33), 'kwargs', None, None), [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 36, 1, 40))], [], None, None)], []),
2544]
2545single_results = [
2546('Interactive', [('Expr', (1, 0, 1, 3), ('BinOp', (1, 0, 1, 3), ('Constant', (1, 0, 1, 1), 1, None), ('Add',), ('Constant', (1, 2, 1, 3), 2, None)))]),
2547]
2548eval_results = [
2549('Expression', ('Constant', (1, 0, 1, 4), None, None)),
2550('Expression', ('BoolOp', (1, 0, 1, 7), ('And',), [('Name', (1, 0, 1, 1), 'a', ('Load',)), ('Name', (1, 6, 1, 7), 'b', ('Load',))])),
2551('Expression', ('BinOp', (1, 0, 1, 5), ('Name', (1, 0, 1, 1), 'a', ('Load',)), ('Add',), ('Name', (1, 4, 1, 5), 'b', ('Load',)))),
2552('Expression', ('UnaryOp', (1, 0, 1, 5), ('Not',), ('Name', (1, 4, 1, 5), 'v', ('Load',)))),
2553('Expression', ('Lambda', (1, 0, 1, 11), ('arguments', [], [], None, [], [], None, []), ('Constant', (1, 7, 1, 11), None, None))),
2554('Expression', ('Dict', (1, 0, 1, 7), [('Constant', (1, 2, 1, 3), 1, None)], [('Constant', (1, 4, 1, 5), 2, None)])),
2555('Expression', ('Dict', (1, 0, 1, 2), [], [])),
2556('Expression', ('Set', (1, 0, 1, 7), [('Constant', (1, 1, 1, 5), None, None)])),
2557('Expression', ('Dict', (1, 0, 5, 6), [('Constant', (2, 6, 2, 7), 1, None)], [('Constant', (4, 10, 4, 11), 2, None)])),
2558('Expression', ('ListComp', (1, 0, 1, 19), ('Name', (1, 1, 1, 2), 'a', ('Load',)), [('comprehension', ('Name', (1, 7, 1, 8), 'b', ('Store',)), ('Name', (1, 12, 1, 13), 'c', ('Load',)), [('Name', (1, 17, 1, 18), 'd', ('Load',))], 0)])),
2559('Expression', ('GeneratorExp', (1, 0, 1, 19), ('Name', (1, 1, 1, 2), 'a', ('Load',)), [('comprehension', ('Name', (1, 7, 1, 8), 'b', ('Store',)), ('Name', (1, 12, 1, 13), 'c', ('Load',)), [('Name', (1, 17, 1, 18), 'd', ('Load',))], 0)])),
2560('Expression', ('ListComp', (1, 0, 1, 20), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'c', ('Load',)), [], 0)])),
2561('Expression', ('ListComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2562('Expression', ('ListComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('List', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2563('Expression', ('SetComp', (1, 0, 1, 20), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'c', ('Load',)), [], 0)])),
2564('Expression', ('SetComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2565('Expression', ('SetComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('List', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2566('Expression', ('GeneratorExp', (1, 0, 1, 20), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'c', ('Load',)), [], 0)])),
2567('Expression', ('GeneratorExp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2568('Expression', ('GeneratorExp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('List', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2569('Expression', ('Compare', (1, 0, 1, 9), ('Constant', (1, 0, 1, 1), 1, None), [('Lt',), ('Lt',)], [('Constant', (1, 4, 1, 5), 2, None), ('Constant', (1, 8, 1, 9), 3, None)])),
2570('Expression', ('Call', (1, 0, 1, 17), ('Name', (1, 0, 1, 1), 'f', ('Load',)), [('Constant', (1, 2, 1, 3), 1, None), ('Constant', (1, 4, 1, 5), 2, None), ('Starred', (1, 10, 1, 12), ('Name', (1, 11, 1, 12), 'd', ('Load',)), ('Load',))], [('keyword', (1, 6, 1, 9), 'c', ('Constant', (1, 8, 1, 9), 3, None)), ('keyword', (1, 13, 1, 16), None, ('Name', (1, 15, 1, 16), 'e', ('Load',)))])),
2571('Expression', ('Call', (1, 0, 1, 10), ('Name', (1, 0, 1, 1), 'f', ('Load',)), [('Starred', (1, 2, 1, 9), ('List', (1, 3, 1, 9), [('Constant', (1, 4, 1, 5), 0, None), ('Constant', (1, 7, 1, 8), 1, None)], ('Load',)), ('Load',))], [])),
2572('Expression', ('Call', (1, 0, 1, 15), ('Name', (1, 0, 1, 1), 'f', ('Load',)), [('GeneratorExp', (1, 1, 1, 15), ('Name', (1, 2, 1, 3), 'a', ('Load',)), [('comprehension', ('Name', (1, 8, 1, 9), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Load',)), [], 0)])], [])),
2573('Expression', ('Constant', (1, 0, 1, 2), 10, None)),
2574('Expression', ('Constant', (1, 0, 1, 8), 'string', None)),
2575('Expression', ('Attribute', (1, 0, 1, 3), ('Name', (1, 0, 1, 1), 'a', ('Load',)), 'b', ('Load',))),
2576('Expression', ('Subscript', (1, 0, 1, 6), ('Name', (1, 0, 1, 1), 'a', ('Load',)), ('Slice', (1, 2, 1, 5), ('Name', (1, 2, 1, 3), 'b', ('Load',)), ('Name', (1, 4, 1, 5), 'c', ('Load',)), None), ('Load',))),
2577('Expression', ('Name', (1, 0, 1, 1), 'v', ('Load',))),
2578('Expression', ('List', (1, 0, 1, 7), [('Constant', (1, 1, 1, 2), 1, None), ('Constant', (1, 3, 1, 4), 2, None), ('Constant', (1, 5, 1, 6), 3, None)], ('Load',))),
2579('Expression', ('List', (1, 0, 1, 2), [], ('Load',))),
2580('Expression', ('Tuple', (1, 0, 1, 5), [('Constant', (1, 0, 1, 1), 1, None), ('Constant', (1, 2, 1, 3), 2, None), ('Constant', (1, 4, 1, 5), 3, None)], ('Load',))),
2581('Expression', ('Tuple', (1, 0, 1, 7), [('Constant', (1, 1, 1, 2), 1, None), ('Constant', (1, 3, 1, 4), 2, None), ('Constant', (1, 5, 1, 6), 3, None)], ('Load',))),
2582('Expression', ('Tuple', (1, 0, 1, 2), [], ('Load',))),
2583('Expression', ('Call', (1, 0, 1, 17), ('Attribute', (1, 0, 1, 7), ('Attribute', (1, 0, 1, 5), ('Attribute', (1, 0, 1, 3), ('Name', (1, 0, 1, 1), 'a', ('Load',)), 'b', ('Load',)), 'c', ('Load',)), 'd', ('Load',)), [('Subscript', (1, 8, 1, 16), ('Attribute', (1, 8, 1, 11), ('Name', (1, 8, 1, 9), 'a', ('Load',)), 'b', ('Load',)), ('Slice', (1, 12, 1, 15), ('Constant', (1, 12, 1, 13), 1, None), ('Constant', (1, 14, 1, 15), 2, None), None), ('Load',))], [])),
2584]
2585main()
2586