Author: Amaury Forgeot d'Arc <amaur...@gmail.com>
Branch: py3.6
Changeset: r95540:3f85fe07a914
Date: 2018-12-30 14:57 +0100
http://bitbucket.org/pypy/pypy/changeset/3f85fe07a914/

Log:    Check conflict between 'global' and variable annotation. This fixes
        the last failure in test_grammar.

diff --git a/pypy/interpreter/astcompiler/symtable.py 
b/pypy/interpreter/astcompiler/symtable.py
--- a/pypy/interpreter/astcompiler/symtable.py
+++ b/pypy/interpreter/astcompiler/symtable.py
@@ -429,8 +429,17 @@
             self.scope.contains_annotated = True
         target = assign.target
         if isinstance(target, ast.Name):
-            # XXX Should check (and fail) for previous 'global' annotation.
             name = target.id
+            old_role = self.scope.lookup_role(name)
+            if assign.simple:
+                if old_role & SYM_GLOBAL:
+                    raise SyntaxError(
+                        "annotated name '%s' can't be global" % name,
+                        assign.lineno, assign.col_offset)
+                if old_role & SYM_NONLOCAL:
+                    raise SyntaxError(
+                        "annotated name '%s' can't be nonlocal" % name,
+                        assign.lineno, assign.col_offset)
             scope = SYM_BLANK
             if assign.simple:
                 scope |= SYM_ANNOTATED
diff --git a/pypy/interpreter/astcompiler/test/test_symtable.py 
b/pypy/interpreter/astcompiler/test/test_symtable.py
--- a/pypy/interpreter/astcompiler/test/test_symtable.py
+++ b/pypy/interpreter/astcompiler/test/test_symtable.py
@@ -494,6 +494,14 @@
         assert exc_global.msg == "annotated name 'x' can't be global"
         assert exc_global.lineno == 3
 
+    def test_annotation_global2(self):
+        src_global = ("def f():\n"
+                      "    global x\n"
+                      "    x: int\n")
+        exc_global = py.test.raises(SyntaxError, self.func_scope, 
src_global).value
+        assert exc_global.msg == "annotated name 'x' can't be global"
+        assert exc_global.lineno == 3
+
     def test_annotation_nonlocal(self):
         src_nonlocal = ("def f():\n"
                         "    x: int\n"
_______________________________________________
pypy-commit mailing list
pypy-commit@python.org
https://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to